@cap-ts/soap-adapter 0.1.6 → 0.1.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,112 +1,430 @@
1
- export type TraceContext = any;
2
- export type CdsEntity = any;
3
- export type SoapHeaderObject = any;
4
1
  /**
5
- * @typedef {import('./_orchestrator').TraceContext} TraceContext
6
- * @typedef {import('./_orchestrator').CdsEntity} CdsEntity
7
- * @typedef {import('./_orchestrator').SoapHeaderObject} SoapHeaderObject
2
+ * @module @cap-ts/soap-adapter/lib
3
+ * @description Public API surface of the `@cap-ts/soap-adapter` library.
4
+ *
5
+ * Exports {@link ApplicationService} — the abstract base class that every
6
+ * per-entity SOAP adapter must extend — along with {@link FORBIDDEN_SOAP_HEADERS}
7
+ * and a set of re-exported utilities (`createRequest`, `getEntityKeyFields`,
8
+ * `dedupByKeys`, `isSoapService`, `read`).
9
+ *
10
+ * The loader (`_loader/index`) discovers subclasses by filename convention,
11
+ * instantiates them per request, and drives them via the orchestrator
12
+ * (`_orchestrator/index`).
13
+ *
14
+ * @see {@link ApplicationService}
15
+ * @see {@link FORBIDDEN_SOAP_HEADERS}
16
+ */
17
+ import type { Request } from '@sap/cds';
18
+ /**
19
+ * Correlation / tracing identifiers forwarded to every hook invocation so
20
+ * that adapter code can emit structured log lines without having to
21
+ * reconstruct the context from the raw CAP request.
22
+ *
23
+ * @interface TraceContext
24
+ * @property {string} correlationId - Platform-level correlation ID (e.g.
25
+ * `x-vcap-request-id` or `x-correlation-id` from the inbound request).
26
+ * @property {string} user - The authenticated user identifier, typically
27
+ * `req.user.id` as resolved by CAP's authentication middleware.
28
+ * @property {string} timestamp - ISO-8601 timestamp captured at the start
29
+ * of the request, used for log ordering and latency calculations.
30
+ */
31
+ interface TraceContext {
32
+ correlationId: string;
33
+ user: string;
34
+ timestamp: string;
35
+ }
36
+ /**
37
+ * Minimal shape of a CAP CSN entity reflection object as seen at runtime.
38
+ * The full `cds.linked` entity carries many more fields; only the subset
39
+ * consumed by the adapter framework is declared here.
40
+ *
41
+ * @interface CdsEntity
42
+ * @property {string} name - Fully qualified entity name, e.g.
43
+ * `'ext.BusinessPartnerSet'`.
44
+ * @property {Record<string, CdsEntityElement>} elements - Map of element
45
+ * (field) name → element descriptor.
46
+ * @property {SoapBindingConfig} [@Soap.binding] - Optional SOAP binding
47
+ * annotation placed on the entity in the `.cds` model.
48
+ * @property {{ name: string }} parent - The parent service or namespace
49
+ * object; `parent.name` is used to look up `cds.services[parentName]`.
50
+ */
51
+ interface CdsEntity {
52
+ name: string;
53
+ elements: Record<string, CdsEntityElement>;
54
+ '@Soap.binding'?: SoapBindingConfig;
55
+ parent: {
56
+ name: string;
57
+ };
58
+ [key: string]: unknown;
59
+ }
60
+ /**
61
+ * Descriptor for a single element (field) of a CDS entity as returned by
62
+ * `cds.linked` reflection.
63
+ *
64
+ * @interface CdsEntityElement
65
+ * @property {string} [type] - CDS type name, e.g. `'cds.String'`.
66
+ * @property {string} [@Soap.path] - XPath-like path within the SOAP
67
+ * response document that this element maps to.
68
+ */
69
+ interface CdsEntityElement {
70
+ type?: string;
71
+ '@Soap.path'?: string;
72
+ [key: string]: unknown;
73
+ }
74
+ /**
75
+ * Value of the `@Soap.binding` annotation on a CDS entity. Populated by
76
+ * the loader after it resolves the adapter class.
77
+ *
78
+ * @interface SoapBindingConfig
79
+ * @property {string} operation - SOAP operation name (WSDL `<operation>`),
80
+ * e.g. `'GetBusinessPartnerCollection'`.
81
+ * @property {new (entity: CdsEntity, req: Request, trace: TraceContext) => BaseAdapterInstance} [resolvedAdapterClass]
82
+ * - The adapter subclass constructor resolved by the loader. Absent until
83
+ * the loader has completed its discovery pass.
84
+ * @property {string} [rootRequest] - Optional XPath root element to wrap
85
+ * the outbound SOAP request payload in.
86
+ * @property {string} [rootResponse] - Optional XPath root element to unwrap
87
+ * from the inbound SOAP response before mapping.
88
+ */
89
+ interface SoapBindingConfig {
90
+ operation: string;
91
+ resolvedAdapterClass?: new (entity: CdsEntity, req: Request, trace: TraceContext) => BaseAdapterInstance;
92
+ rootRequest?: string;
93
+ rootResponse?: string;
94
+ }
95
+ /**
96
+ * A single SOAP header entry. Either a static object passed directly to
97
+ * `header()` or the resolved return value of a `SoapHeaderEvaluator`
98
+ * callback.
99
+ *
100
+ * @interface SoapHeaderObject
101
+ * @property {*} [value] - Header value (string or structured object
102
+ * depending on the WSDL contract).
103
+ * @property {string} [name] - Local name of the SOAP header element.
104
+ * @property {string} [prefix] - XML namespace prefix, e.g. `'wsse'`.
105
+ * @property {string} [xmlns] - XML namespace URI bound to `prefix`.
8
106
  */
107
+ interface SoapHeaderObject {
108
+ value?: unknown;
109
+ name?: string;
110
+ prefix?: string;
111
+ xmlns?: string;
112
+ [key: string]: unknown;
113
+ }
9
114
  /**
10
- * Abstract foundational class defining structural contracts and lifecycle hook registration chains
11
- * for CAP-to-SOAP adapter overrides. This class cannot be instantiated directly.
115
+ * Minimal structural contract that every `ApplicationService` instance must
116
+ * satisfy so the orchestrator can dispatch hooks without knowing the
117
+ * concrete subclass.
118
+ *
119
+ * @interface BaseAdapterInstance
120
+ * @property {Record<string, Array<Function>>} _requestHandlers - Per-entity
121
+ * ordered list of outbound payload transformers registered via
122
+ * {@link ApplicationService#request}.
123
+ * @property {Record<string, Function>} _mockHandlers - Per-entity mock
124
+ * replacements registered via {@link ApplicationService#mock}. Only one
125
+ * mock per entity; the last registration wins.
126
+ * @property {Record<string, Array<SoapHeaderObject|Function>>} _headerHandlers
127
+ * - Per-entity header providers registered via {@link ApplicationService#header}.
128
+ * @property {Record<string, Array<Function>>} _responseHandlers - Per-entity
129
+ * ordered list of response mappers registered via
130
+ * {@link ApplicationService#response}.
131
+ */
132
+ interface BaseAdapterInstance {
133
+ _requestHandlers: Record<string, Array<(payload: unknown, req: Request) => Promise<unknown> | unknown>>;
134
+ _mockHandlers: Record<string, (req: Request, payload: unknown) => Promise<unknown>>;
135
+ _headerHandlers: Record<string, Array<SoapHeaderObject | ((req: Request, payload: unknown) => Promise<SoapHeaderObject> | SoapHeaderObject)>>;
136
+ _responseHandlers: Record<string, Array<(rows: object[], req: Request) => Promise<object[]> | object[]>>;
137
+ }
138
+ /**
139
+ * Abstract base class for per-entity SOAP adapters.
140
+ *
141
+ * Consumers subclass this, override {@link ApplicationService#init} to
142
+ * register any combination of {@link ApplicationService#header},
143
+ * {@link ApplicationService#request}, {@link ApplicationService#mock}, and
144
+ * {@link ApplicationService#response} hooks, then export the subclass from a
145
+ * file named `<EntityShortName>.js` or `<EntityShortName>.ts` placed next to
146
+ * the service's `.cds` file.
147
+ *
148
+ * **Contract:**
149
+ * - **One instance per request.** Do not cache request-scoped state on
150
+ * `this` across requests. `entity`, `req`, and `traceContext` are
151
+ * populated fresh for every invocation.
152
+ * - **`init()` is called once, from the constructor**, after the request
153
+ * fields are populated. Register all hooks there.
154
+ * - **Hooks are dispatched by unqualified entity short-name** (e.g.
155
+ * `'BusinessPartner'`, not `'ext.BusinessPartner'`). The `targets`
156
+ * parameter of each registration method accepts strings, CSN entity
157
+ * objects, arrays of either, or comma-separated strings.
12
158
  *
13
159
  * @abstract
160
+ * @example
161
+ * // Minimal adapter for a "ProductSet" entity:
162
+ * class ProductSet extends ApplicationService {
163
+ * init() {
164
+ * this.request('ProductSet', async (req) => ({
165
+ * ProductID: req.data.ID,
166
+ * }));
167
+ * this.response('ProductSet', (req, rows) =>
168
+ * rows.map(r => ({ ...r, _source: 'soap' }))
169
+ * );
170
+ * }
171
+ * }
172
+ * module.exports = { ProductSet };
14
173
  */
15
- export class ApplicationService {
16
- /**
17
- * Initializes the abstract service base layout.
18
- * @param {CdsEntity} entity - Contextual meta-reflection model representing the current execution entity instance.
19
- * @param {cds.Request} req - The incoming runtime context parameter bundle payload managed by the active application framework.
20
- * @param {TraceContext} traceContext - Unique execution tracking identifier context map used for logging.
21
- * @throws {TypeError} If this abstract class is directly instantiated via `new ApplicationService()`.
22
- */
23
- constructor(entity: CdsEntity, req: cds.Request, traceContext: TraceContext);
24
- entity: any;
25
- req: cds.Request;
26
- traceContext: any;
27
- _requestHandlers: {};
28
- _responseHandlers: {};
29
- _mockHandlers: {};
30
- _headerHandlers: {};
31
- entities: any;
32
- /**
33
- * Internal framework initialization lifecycle wrapper.
34
- * Safe fallback that child classes can call via super._superInit() if wanted.
35
- * @private
174
+ declare class ApplicationService {
175
+ /**
176
+ * Frozen array of HTTP header names that must never be forwarded to a
177
+ * SOAP backend. Used by {@link ApplicationService.stripSensitiveHeaders}.
178
+ * @static
179
+ * @readonly
180
+ * @public
36
181
  */
37
- private _superInit;
182
+ static readonly FORBIDDEN_SOAP_HEADERS: readonly string[];
38
183
  /**
39
- * Abstract initialization sequence triggered automatically during instance generation.
40
- * Must be overridden in child classes to establish event listeners.
41
- * @abstract
42
- * @throws {Error} If the derived child class does not implement this method.
43
- * @returns {void}
184
+ * CSN entity reflection object for the entity this adapter instance
185
+ * serves. Populated by the constructor before `init()` is called.
186
+ * @public
44
187
  */
45
- init(): void;
188
+ entity: CdsEntity;
46
189
  /**
47
- * Internal framework utility to convert single or multi-target inputs down
48
- * to a flat list of clean, unqualified short name string token keys.
49
- * Fully handles: Arrays of CSN Objects, single Objects, and raw strings.
50
- * @param {string|Object|Array.<string|Object>} targets - The input target(s) to normalize into a flat list of unqualified entity names.
51
- * @returns {Array.<string>} A flat list of unqualified entity name strings.
52
- * @private
190
+ * The current CAP request. Available as `this.req` inside all hooks.
191
+ * @public
53
192
  */
54
- private _resolveEntityNames;
193
+ req: Request;
55
194
  /**
56
- * @callback SoapHeaderEvaluator
57
- * @param {cds.Request} req - The incoming CAP request context.
58
- * @param {*} [data] - The optional secondary payload data context.
59
- * @returns {Promise.<SoapHeaderObject>|SoapHeaderObject}
195
+ * Correlation / tracing identifiers forwarded from the orchestrator.
196
+ * Forwarded to every hook invocation for structured logging.
197
+ * @public
60
198
  */
199
+ traceContext: TraceContext;
61
200
  /**
62
- * Registers a custom SOAP header factory interceptor or a static structural payload value for a specific entity.
63
- * @param {string|Object|Array.<string|Object>} targets - The input target(s) to normalize into a flat list of unqualified entity names.
64
- * @param {SoapHeaderObject|SoapHeaderEvaluator} handler - A static header matching object configurations or an executable factory generator function.
65
- * @throws {Error} If the provided handler is neither a functional execution block nor an object structure.
66
- * @returns {void}
201
+ * All entities exposed by the parent CAP service, keyed by unqualified
202
+ * short-name. Populated automatically from `cds.services[parentName].entities`
203
+ * in the constructor. Empty object `{}` when the parent service cannot
204
+ * be resolved (e.g. in unit tests that do not boot a full CAP server).
205
+ * @public
206
+ */
207
+ entities: Record<string, CdsEntity>;
208
+ /**
209
+ * Per-entity ordered list of outbound payload transformer functions
210
+ * registered via {@link ApplicationService#request}.
211
+ * @protected
212
+ */
213
+ protected _requestHandlers: Record<string, Array<(payload: unknown, req: Request) => Promise<unknown> | unknown>>;
214
+ /**
215
+ * Per-entity ordered list of response mapper functions registered via
216
+ * {@link ApplicationService#response}.
217
+ * @protected
218
+ */
219
+ protected _responseHandlers: Record<string, Array<(rows: object[], req: Request) => Promise<object[]> | object[]>>;
220
+ /**
221
+ * Per-entity mock replacement functions registered via
222
+ * {@link ApplicationService#mock}. Only one mock per entity; the last
223
+ * registration wins.
224
+ * @protected
225
+ */
226
+ protected _mockHandlers: Record<string, (req: Request, payload: unknown) => Promise<unknown>>;
227
+ /**
228
+ * Per-entity header providers (static objects or evaluator functions)
229
+ * registered via {@link ApplicationService#header}.
230
+ * @protected
67
231
  */
68
- header(targets: string | Object | Array<string | Object>, handler: SoapHeaderObject | ((req: cds.Request, data?: any) => Promise<SoapHeaderObject> | SoapHeaderObject)): void;
232
+ protected _headerHandlers: Record<string, Array<SoapHeaderObject | ((req: Request, payload: unknown) => Promise<SoapHeaderObject> | SoapHeaderObject)>>;
69
233
  /**
70
- * @callback SoapRequestEvaluator
71
- * @param {cds.Request} req - The incoming CAP request context.
72
- * @param {*} [data] - The optional secondary payload data context.
73
- * @returns {Promise.<*>|*}
234
+ * Return a shallow copy of `headers` with every key that appears in
235
+ * {@link FORBIDDEN_SOAP_HEADERS} removed (comparison is
236
+ * case-insensitive — keys are lower-cased before matching).
237
+ *
238
+ * Non-object or falsy input returns an empty object `{}` rather than
239
+ * throwing, so callers can safely pass `req.headers ?? {}` without a
240
+ * guard.
241
+ *
242
+ * The allowlist is exposed as `ApplicationService.FORBIDDEN_SOAP_HEADERS`
243
+ * (frozen). Consumers can extend it by cloning the array and adding
244
+ * extra entries; mutating the exported constant throws in strict mode.
245
+ *
246
+ * @param {Record<string, *>} headers - The raw HTTP headers object to
247
+ * sanitise (e.g. `req.headers`).
248
+ * @returns {Record<string, *>} A new object containing only the headers
249
+ * that are safe to forward to the SOAP backend.
250
+ * @example
251
+ * // Inside a header() hook:
252
+ * this.header(Entity, (req) =>
253
+ * ApplicationService.stripSensitiveHeaders(req.headers ?? {})
254
+ * );
255
+ * @static
256
+ * @public
74
257
  */
258
+ static stripSensitiveHeaders(headers: Record<string, unknown>): Record<string, unknown>;
75
259
  /**
76
- * Appends a pre-flight payload manipulation interceptor function to the execution chain of an entity.
77
- * @param {string|Object|Array.<string|Object>} targets - The unqualified short name string or the compiled CSN Entity Object definition.
78
- * @param {SoapRequestEvaluator} handler - Callback function mutating incoming outbound arguments.
79
- * @throws {Error} If the handler input fails functional type evaluation checks.
260
+ * Initialise the adapter instance for a single CAP request.
261
+ *
262
+ * Performs the following steps in order:
263
+ * 1. Guards against direct instantiation (abstract-class enforcement).
264
+ * 2. Stores `entity`, `req`, and `traceContext` on `this`.
265
+ * 3. Initialises the four empty handler registries
266
+ * (`_requestHandlers`, `_responseHandlers`, `_mockHandlers`,
267
+ * `_headerHandlers`).
268
+ * 4. Resolves the parent service name from the entity reflection and
269
+ * binds `this.entities` from `cds.services[parentName].entities`.
270
+ * 5. Calls `_superInit()` (framework extension point, currently a no-op).
271
+ * 6. Calls `init()` so the subclass can register its hooks.
272
+ *
273
+ * @param {CdsEntity} entity - CSN entity reflection for the entity this
274
+ * adapter serves (e.g. `srv.entities.BusinessUserSet`).
275
+ * @param {Request} req - The current CAP request. Available as
276
+ * `this.req` inside all hook callbacks.
277
+ * @param {TraceContext} traceContext - Correlation IDs for structured
278
+ * logs; forwarded to every hook invocation.
279
+ * @throws {TypeError} If instantiated directly (i.e. `new.target ===
280
+ * ApplicationService`) instead of via a concrete subclass.
281
+ * @public
282
+ */
283
+ constructor(entity: CdsEntity, req: Request, traceContext: TraceContext);
284
+ /**
285
+ * Framework extension point called by the constructor immediately before
286
+ * {@link ApplicationService#init}. Currently a no-op; reserved for
287
+ * future default initialisation steps (e.g. injecting framework-level
288
+ * hooks or populating shared metadata).
289
+ *
290
+ * Subclasses **may** call `super._superInit()` from their own `init()`
291
+ * for forward-compatibility, but nothing depends on it today.
292
+ *
293
+ * Visibility is `protected` (not `private`) because the documented
294
+ * override contract via `super._superInit()` requires subclass access.
295
+ *
80
296
  * @returns {void}
297
+ * @protected
298
+ */
299
+ protected _superInit(): void;
300
+ /**
301
+ * Lifecycle hook called once from the constructor after all instance
302
+ * fields are populated. Subclasses **must** override this method and
303
+ * use it to register their SOAP hooks via `header()`, `request()`,
304
+ * `mock()`, and/or `response()`.
305
+ *
306
+ * The base implementation throws unconditionally so that a missing
307
+ * override is caught at instantiation time rather than silently
308
+ * producing a no-op adapter.
309
+ *
310
+ * @abstract
311
+ * @throws {Error} Always — subclasses must override this method.
312
+ * @returns {void}
313
+ * @public
314
+ */
315
+ init(): void;
316
+ /**
317
+ * Normalise a `targets` argument into a flat, deduplicated list of
318
+ * unqualified entity short-names used as internal dispatch keys.
319
+ *
320
+ * Accepted input forms:
321
+ * - **CSN entity object** (`{ name: 'ext.BusinessPartner', … }`) →
322
+ * returns `['BusinessPartner']` (last segment after the last `.`).
323
+ * - **Qualified string** (`'ext.BusinessPartner'`) → same as above.
324
+ * - **Unqualified string** (`'BusinessPartner'`) → returned as-is.
325
+ * - **Comma-separated string** (`'A,ext.B'`) → split, trimmed, and
326
+ * each entry normalised individually.
327
+ * - **Array** of any of the above → recursively flattened.
328
+ * - `null` / `undefined` / empty string → returns `[]`.
329
+ *
330
+ * @param {string|CdsEntity|Array<string|CdsEntity>|null|undefined} targets
331
+ * - One or more entity references to normalise.
332
+ * @returns {string[]} Zero or more unqualified entity short-names.
333
+ * @private
81
334
  */
82
- request(targets: string | Object | Array<string | Object>, handler: (req: cds.Request, data?: any) => Promise<any> | any): void;
335
+ private _resolveEntityNames;
83
336
  /**
84
- * @callback SoapMockEvaluator
85
- * @param {cds.Request} req - The incoming CAP request context.
86
- * @param {*} [data] - The optional secondary payload data context.
87
- * @returns {Promise.<*>|*}
337
+ * Register SOAP header providers for one or more entities.
338
+ *
339
+ * `handler` may be either:
340
+ * - A **static** {@link SoapHeaderObject} that is attached verbatim to
341
+ * every outbound SOAP call for the matched entities.
342
+ * - An **evaluator function** `(req, data) => SoapHeaderObject` (sync or
343
+ * async) that is called per request and may inspect `req` to build the
344
+ * header dynamically.
345
+ *
346
+ * Multiple registrations for the same entity are all invoked in
347
+ * registration order. The same handler reference passed twice for the
348
+ * same entity is de-duplicated (only the first registration is kept).
349
+ *
350
+ * Common use: strip sensitive inbound HTTP headers before forwarding
351
+ * them to the SOAP backend — see
352
+ * {@link ApplicationService.stripSensitiveHeaders}.
353
+ *
354
+ * @param {string|CdsEntity|Array<string|CdsEntity>} targets - One or
355
+ * more entity references that this header provider applies to.
356
+ * @param {SoapHeaderObject|((req: Request, payload: *) => Promise<SoapHeaderObject>|SoapHeaderObject)} handler
357
+ * - Static header object or evaluator function.
358
+ * @throws {Error} If `handler` is neither a function nor an object.
359
+ * @returns {void}
360
+ * @public
88
361
  */
362
+ header(targets: string | CdsEntity | Array<string | CdsEntity>, handler: SoapHeaderObject | ((req: Request, payload: unknown) => Promise<SoapHeaderObject> | SoapHeaderObject)): void;
89
363
  /**
90
- * Registers a single intercept sandbox bypass mock handler function for an entity, overriding native network requests entirely.
91
- * @param {string|Object|Array.<string|Object>} targets - The input target(s) to normalize into a flat list of unqualified entity names.
92
- * @param {SoapMockEvaluator} handler - Intercept bypass simulation callback executing sandboxed returns.
93
- * @throws {Error} If the handler input fails functional type evaluation checks.
364
+ * Register a hook that shapes the outbound SOAP payload for one or more
365
+ * entities.
366
+ *
367
+ * The return value of `handler` replaces the payload that the
368
+ * orchestrator would otherwise build from the CAP request. Multiple
369
+ * registrations for the same entity run in registration order; each
370
+ * invocation receives the output of the previous stage. The same
371
+ * handler reference passed twice is de-duplicated.
372
+ *
373
+ * @param {string|CdsEntity|Array<string|CdsEntity>} targets - One or
374
+ * more entity references that this request transformer applies to.
375
+ * @param {(payload: *, req: Request) => Promise<*>|*} handler - A
376
+ * function that receives the current payload and the CAP request, and
377
+ * returns the transformed payload (sync or async).
378
+ * @throws {Error} If `handler` is not a function.
94
379
  * @returns {void}
380
+ * @public
95
381
  */
96
- mock(targets: string | Object | Array<string | Object>, handler: (req: cds.Request, data?: any) => Promise<any> | any): void;
382
+ request(targets: string | CdsEntity | Array<string | CdsEntity>, handler: (payload: unknown, req: Request) => Promise<unknown> | unknown): void;
97
383
  /**
98
- * @callback SoapResponseEvaluator
99
- * @param {cds.Request} req - The incoming CAP request context.
100
- * @param {any[]} data - The response data context.
101
- * @returns {Promise.<Array.<Object>>|Array.<Object>}
102
- */
384
+ * Register a mock that fully replaces the SOAP round-trip for the given
385
+ * entity/entities.
386
+ *
387
+ * When a mock is registered, the orchestrator returns the mock's value
388
+ * directly instead of calling the SOAP backend. Only **one** mock per
389
+ * entity is kept — the last registration wins (unlike `request` /
390
+ * `response` which accumulate).
391
+ *
392
+ * Intended for unit tests. Not subject to error sanitisation — any
393
+ * exception thrown by the mock is surfaced as-is to the caller.
394
+ *
395
+ * @param {string|CdsEntity|Array<string|CdsEntity>} targets - One or
396
+ * more entity references to mock.
397
+ * @param {(req: Request, payload: *) => Promise<*>|*} handler - A
398
+ * function that receives the CAP request and the current payload, and
399
+ * returns the mock response (sync or async).
400
+ * @throws {Error} If `handler` is not a function.
401
+ * @returns {void}
402
+ * @public
403
+ */
404
+ mock(targets: string | CdsEntity | Array<string | CdsEntity>, handler: (req: Request, payload: unknown) => Promise<unknown>): void;
103
405
  /**
104
- * Appends a post-flight response extraction array mapping transformation interceptor function to the execution chain of an entity.
105
- * @param {string|Object|Array.<string|Object>} targets - The unqualified short name string or the compiled CSN Entity Object definition.
106
- * @param {SoapResponseEvaluator} handler - Translation mapper formatting downstream runtime array structures.
107
- * @throws {Error} If the handler input fails functional type evaluation checks.
406
+ * Register a hook that maps the raw SOAP response array into the flat
407
+ * row shape that CAP expects for the target entity.
408
+ *
409
+ * Multiple registrations for the same entity run in registration order;
410
+ * each invocation receives the output of the previous stage. Unlike
411
+ * `header` and `request`, this hook is **not** de-duplicated —
412
+ * registering the same handler reference twice causes it to run twice.
413
+ *
414
+ * @param {string|CdsEntity|Array<string|CdsEntity>} targets - One or
415
+ * more entity references that this response mapper applies to.
416
+ * @param {(rows: object[], req: Request) => Promise<object[]>|object[]} handler
417
+ * - A function that receives the current row array and the CAP
418
+ * request, and returns the transformed row array (sync or async).
419
+ * @throws {Error} If `handler` is not a function.
108
420
  * @returns {void}
421
+ * @public
109
422
  */
110
- response(targets: string | Object | Array<string | Object>, handler: (req: cds.Request, data: any[]) => Promise<Array<Object>> | Array<Object>): void;
423
+ response(targets: string | CdsEntity | Array<string | CdsEntity>, handler: (rows: object[], req: Request) => Promise<object[]> | object[]): void;
111
424
  }
425
+ declare const createRequest: typeof import("./_request").createRequest;
426
+ declare const getEntityKeyFields: typeof import("./_util/entity").getEntityKeyFields, dedupByKeys: typeof import("./_util/entity").dedupByKeys, isSoapService: typeof import("./_util/entity").isSoapService;
427
+ declare const read: typeof import("./_read").read;
428
+ export type { ReadOptions } from './_read';
429
+ export { ApplicationService, createRequest, getEntityKeyFields, dedupByKeys, isSoapService, read, };
112
430
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../.types/lib/index.js"],"names":[],"mappings":";;;AAAA;;;;GAIG;AAEH;;;;;GAKG;AACH;IACI;;;;;;OAMG;IACH,oBALW,SAAS,OACT,GAAG,CAAC,OAAO,gBACX,YAAY,EAiCtB;IA1BG,YAAoB;IACpB,iBAAc;IACd,kBAAgC;IAGhC,qBAA0B;IAC1B,sBAA2B;IAC3B,kBAAuB;IACvB,oBAAyB;IAUrB,cAA8D;IAUtE;;;;OAIG;IACH,mBAEC;IAED;;;;;;OAMG;IACH,QAFa,IAAI,CAIhB;IAED;;;;;;;OAOG;IACH,4BA8BC;IAED;;;;;OAKG;IAEH;;;;;;OAMG;IACH,gBALW,MAAM,GAAC,MAAM,GAAC,KAAK,CAAE,MAAM,GAAC,MAAM,CAAC,WACnC,gBAAgB,UARhB,GAAG,CAAC,OAAO,SACX,GAAC,KACC,OAAO,CAAE,gBAAgB,CAAC,GAAC,gBAAgB,CAMT,GAElC,IAAI,CAgBhB;IAED;;;;;OAKG;IAEH;;;;;;OAMG;IACH,iBALW,MAAM,GAAC,MAAM,GAAC,KAAK,CAAE,MAAM,GAAC,MAAM,CAAC,iBAPnC,GAAG,CAAC,OAAO,SACX,GAAC,KACC,OAAO,CAAE,GAAC,CAAC,GAAC,GAAC,GAQb,IAAI,CAYhB;IAED;;;;;OAKG;IAEH;;;;;;OAMG;IACH,cALW,MAAM,GAAC,MAAM,GAAC,KAAK,CAAE,MAAM,GAAC,MAAM,CAAC,iBAPnC,GAAG,CAAC,OAAO,SACX,GAAC,KACC,OAAO,CAAE,GAAC,CAAC,GAAC,GAAC,GAQb,IAAI,CAShB;IAEA;;;;;MAKE;IAEH;;;;;;OAMG;IACH,kBALW,MAAM,GAAC,MAAM,GAAC,KAAK,CAAE,MAAM,GAAC,MAAM,CAAC,iBAPnC,GAAG,CAAC,OAAO,QACX,GAAG,EAAE,KACH,OAAO,CAAE,KAAK,CAAE,MAAM,CAAC,CAAC,GAAC,KAAK,CAAE,MAAM,CAAC,GAQvC,IAAI,CAUhB;CACJ"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../build/src/lib/index.ts"],"names":[],"mappings":"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"}