CDS Views Part 9: Parameters and Filtering
Define CDS views with input parameters, use $parameters in WHERE, calculations and path filters, default parameters from system fields, and pass parameters from ABAP. Learn when parameters are the right tool and when a simple WHERE by the consumer is better.
Explanation
📌 KEY POINTS
✅ with parameters defines mandatory inputs; inside the view they are used as $parameters.<name> in WHERE, calculations, CASE and path filters.
✅ @Environment.systemField (e.g. #SYSTEM_DATE, #SYSTEM_LANGUAGE) fills a parameter automatically when the ABAP consumer does not pass it.
✅ Parameters are right when the value changes the calculation itself (key date, target currency, language) — not for plain row filters.
⚠️ Passing parameters from ABAP needs strict ABAP SQL syntax (@ host variables, commas) — this is one of the few places where a classic report must use modern SQL.
━━━━━━━━━━━━━━━━━━━━
▶ WHERE WE ARE
Part 8 restricted rows by user. Now we let the consumer supply values that shape the result.
━━━━━━━━━━━━━━━━━━━━
▶ 1. DEFINING PARAMETERS
- define view entity ZX with parameters p_keydate : abap.dats, p_currency : waers as select from …
- Types: built-in abap.* types or data elements.
- All parameters are mandatory unless defaulted by @Environment.systemField.
━━━━━━━━━━━━━━━━━━━━
▶ 2. USING PARAMETERS
- WHERE erdat <= $parameters.p_keydate.
- Calculations: dats_days_between( erdat, $parameters.p_keydate ).
- Path filters: _Text[1: Language = $parameters.p_language].
- Currency conversion target: target_currency => $parameters.p_currency.
━━━━━━━━━━━━━━━━━━━━
▶ 3. SYSTEM FIELD DEFAULTS
- @Environment.systemField: #SYSTEM_DATE, #SYSTEM_LANGUAGE, #CLIENT, #USER.
- Consumer may omit the parameter; the runtime fills it.
- For simple "today" or "logon language" needs, $session variables (Part 2) avoid parameters entirely.
━━━━━━━━━━━━━━━━━━━━
▶ 4. PASSING FROM ABAP
- SELECT … FROM zview( p_keydate = @lv_date ) … — strict ABAP SQL with @ and comma-separated field list.
- Views with parameters propagate: a view selecting from a parameterized view must pass the parameters on.
━━━━━━━━━━━━━━━━━━━━
▶ 5. PARAMETERS VS WHERE
- Row filters (sales org, customer, date range) → let the consumer filter with WHERE; the optimizer pushes it down anyway.
- Parameters make reuse harder: every consumer must supply them; OData services expose them as mandatory inputs and Fiori elements show a parameter dialog.
- Use parameters when the value is needed inside a calculation or aggregation (key date ageing, currency conversion, "as of" logic).
━━━━━━━━━━━━━━━━━━━━
▶ STEP BY STEP
- Build ZI_OpenOrdersKeyDate with p_keydate and language parameter defaulted from #SYSTEM_LANGUAGE.
- Filter open orders (overall status not completed) created on or before the key date; calculate age at key date.
- Call it from an SE38 report with a key-date PARAMETER, omitting the language.
- Compare: would a WHERE on CreationDate by the consumer be enough? Decide per field.
✅ CHECKPOINT: you can define, default and pass CDS parameters and justify when not to use them.
Code example
// ===== STEP 1: view with parameters =====@AccessControl.authorizationCheck: #NOT_REQUIRED@EndUserText.label: 'Open sales orders at key date'define view entity ZI_OpenOrdersKeyDate with parameters p_keydate : abap.dats, @Environment.systemField: #SYSTEM_LANGUAGE p_language : spras as select from vbak association [0..*] to ZI_SalesOrderTypeText as _TypeText on $projection.SalesOrderType = _TypeText.SalesOrderType{ key vbeln as SalesOrder, auart as SalesOrderType, // ===== STEP 2: parameter in path filter and calculation ===== _TypeText[1: Language = $parameters.p_language].SalesOrderTypeName as SalesOrderTypeName, erdat as CreationDate, dats_days_between( erdat, $parameters.p_keydate ) as AgeAtKeyDate, kunnr as SoldToParty, @Semantics.amount.currencyCode: 'TransactionCurrency' netwr as NetAmount, waerk as TransactionCurrency}where erdat <= $parameters.p_keydate and gbstk <> 'C' * ===== STEP 3: SE38 report passing the parameter =====REPORT zcds_open_orders_keydate. TYPES: BEGIN OF ty_open, salesorder TYPE vbeln_va, salesordertypename TYPE bezei20, ageatkeydate TYPE i, END OF ty_open. DATA: lt_open TYPE STANDARD TABLE OF ty_open, ls_open TYPE ty_open. PARAMETERS p_date TYPE sy-datum DEFAULT sy-datum. START-OF-SELECTION.* Parameter passing requires strict ABAP SQL (@, commas) - documented exception.* p_language is omitted: filled from the logon language by @Environment.systemField. SELECT salesorder, salesordertypename, ageatkeydate FROM zi_openorderskeydate( p_keydate = @p_date ) INTO TABLE @lt_open. * ===== STEP 4: classic processing of the result ===== SORT lt_open BY ageatkeydate DESCENDING. LOOP AT lt_open INTO ls_open. WRITE: / ls_open-salesorder, ls_open-salesordertypename, ls_open-ageatkeydate. ENDLOOP.Real project scenario
A team built its sales-order CDS views with parameters for sales organization, customer and date range "to make filtering fast". Every Fiori app on top showed a parameter dialog before any data appeared, and other reports could not reuse the views without inventing dummy values.
In the redesign, those filters became normal fields filtered by consumers with WHERE and the Fiori filter bar. Only one parameter remained — the key date for the backlog ageing calculation, where the value really changes the result. Performance stayed the same because the database pushed the WHERE conditions down anyway.
Common mistakes
- Using parameters for simple row filters that consumers could apply with WHERE.
- Forgetting that views on top of a parameterized view must pass the parameters on.
- Trying to pass parameters with classic non-strict SQL syntax.
- Not defaulting language/date parameters with @Environment.systemField.
- Parameter types that do not match the compared field (conversion issues).
Best practices
- Use parameters only when the value drives a calculation.
- Default system-derived values with @Environment.systemField, or use $session variables.
- Type parameters with data elements for clear labels in OData.
- Keep parameter names meaningful (P_KeyDate, P_TargetCurrency).
- Document parameters for consumers and OData clients.
Interview angle
Questions: "When would you use CDS parameters?", "How do you pass a parameter from ABAP?", "What is @Environment.systemField?"
Strong answer: parameters (with parameters, $parameters.x) for values that change calculations — key date, currency, language; plain row filters should be consumer WHERE because parameters reduce reuse and force OData/Fiori parameter dialogs. From ABAP: SELECT … FROM view( p = @value ) in strict SQL. @Environment.systemField defaults a parameter from system date, language, client or user when omitted.
Practice this lesson
Quick check
1. A CDS parameter p_language is annotated with @Environment.systemField: #SYSTEM_LANGUAGE. What happens if the ABAP consumer does not pass it?
2. How is an input parameter p_keydate referenced inside a CDS view entity?
3. When is a CDS input parameter the right choice instead of a consumer WHERE condition?
Interview questions
1. A team built all sales CDS views with parameters for sales org, customer and date range "for performance". Fiori apps now show a parameter dialog and other reports cannot reuse the views. Evaluate the design.
Answer it in your own words first, then compare.
2. A condition validity report must always evaluate data as of one key date, and the age of each record depends on that date. How would you model this in CDS?
Answer it in your own words first, then compare.
Reference-verified: the steps are checked against official SAP documentation and tutorials, and object and field names in the sample code are checked for consistency. The code has not been compiled or run on an SAP system by ERPClimb. Syntax marked release-dependent varies by SAP release, so check it in your own system.
More lessons in this topic
- CDS Views Part 1: What CDS Is and Your First View Entity
- CDS Views Part 10: Performance and Troubleshooting
- CDS Views Part 2: Joins, Expressions, CASE, CAST and Functions
- CDS Views Part 3: Aggregation and Analytical Annotations
- CDS Views Part 4: CDS View Entity vs Classic (DDIC-Based) CDS View
- CDS Views Part 5: VDM Layering — Basic, Composite and Consumption Views
- CDS Views Part 6: Associations and Cardinality
- CDS Views Part 7: Annotations for Semantics, Texts, Search and UI