UNPKG

lambda-live-debugger

Version:

Debug Lambda functions locally like it is running in the cloud

662 lines (643 loc) 19.8 kB
'use strict'; var protocolHttp = require('@smithy/protocol-http'); var utilMiddleware = require('@smithy/util-middleware'); const deref = (schemaRef) => { if (typeof schemaRef === "function") { return schemaRef(); } return schemaRef; }; const operation = (namespace, name, traits, input, output) => ({ name, namespace, traits, input, output, }); const schemaDeserializationMiddleware = (config) => (next, context) => async (args) => { const { response } = await next(args); const { operationSchema } = utilMiddleware.getSmithyContext(context); const [, ns, n, t, i, o] = operationSchema ?? []; try { const parsed = await config.protocol.deserializeResponse(operation(ns, n, t, i, o), { ...config, ...context, }, response); return { response, output: parsed, }; } catch (error) { Object.defineProperty(error, "$response", { value: response, enumerable: false, writable: false, configurable: false, }); if (!("$metadata" in error)) { const hint = `Deserialization error: to see the raw response, inspect the hidden field {error}.$response on this object.`; try { error.message += "\n " + hint; } catch (e) { if (!context.logger || context.logger?.constructor?.name === "NoOpLogger") { console.warn(hint); } else { context.logger?.warn?.(hint); } } if (typeof error.$responseBodyText !== "undefined") { if (error.$response) { error.$response.body = error.$responseBodyText; } } try { if (protocolHttp.HttpResponse.isInstance(response)) { const { headers = {} } = response; const headerEntries = Object.entries(headers); error.$metadata = { httpStatusCode: response.statusCode, requestId: findHeader(/^x-[\w-]+-request-?id$/, headerEntries), extendedRequestId: findHeader(/^x-[\w-]+-id-2$/, headerEntries), cfId: findHeader(/^x-[\w-]+-cf-id$/, headerEntries), }; } } catch (e) { } } throw error; } }; const findHeader = (pattern, headers) => { return (headers.find(([k]) => { return k.match(pattern); }) || [void 0, void 0])[1]; }; const schemaSerializationMiddleware = (config) => (next, context) => async (args) => { const { operationSchema } = utilMiddleware.getSmithyContext(context); const [, ns, n, t, i, o] = operationSchema ?? []; const endpoint = context.endpointV2?.url && config.urlParser ? async () => config.urlParser(context.endpointV2.url) : config.endpoint; const request = await config.protocol.serializeRequest(operation(ns, n, t, i, o), args.input, { ...config, ...context, endpoint, }); return next({ ...args, request, }); }; const deserializerMiddlewareOption = { name: "deserializerMiddleware", step: "deserialize", tags: ["DESERIALIZER"], override: true, }; const serializerMiddlewareOption = { name: "serializerMiddleware", step: "serialize", tags: ["SERIALIZER"], override: true, }; function getSchemaSerdePlugin(config) { return { applyToStack: (commandStack) => { commandStack.add(schemaSerializationMiddleware(config), serializerMiddlewareOption); commandStack.add(schemaDeserializationMiddleware(config), deserializerMiddlewareOption); config.protocol.setSerdeContext(config); }, }; } class Schema { name; namespace; traits; static assign(instance, values) { const schema = Object.assign(instance, values); return schema; } static [Symbol.hasInstance](lhs) { const isPrototype = this.prototype.isPrototypeOf(lhs); if (!isPrototype && typeof lhs === "object" && lhs !== null) { const list = lhs; return list.symbol === this.symbol; } return isPrototype; } getName() { return this.namespace + "#" + this.name; } } class ListSchema extends Schema { static symbol = Symbol.for("@smithy/lis"); name; traits; valueSchema; symbol = ListSchema.symbol; } const list = (namespace, name, traits, valueSchema) => Schema.assign(new ListSchema(), { name, namespace, traits, valueSchema, }); class MapSchema extends Schema { static symbol = Symbol.for("@smithy/map"); name; traits; keySchema; valueSchema; symbol = MapSchema.symbol; } const map = (namespace, name, traits, keySchema, valueSchema) => Schema.assign(new MapSchema(), { name, namespace, traits, keySchema, valueSchema, }); class OperationSchema extends Schema { static symbol = Symbol.for("@smithy/ope"); name; traits; input; output; symbol = OperationSchema.symbol; } const op = (namespace, name, traits, input, output) => Schema.assign(new OperationSchema(), { name, namespace, traits, input, output, }); class StructureSchema extends Schema { static symbol = Symbol.for("@smithy/str"); name; traits; memberNames; memberList; symbol = StructureSchema.symbol; } const struct = (namespace, name, traits, memberNames, memberList) => Schema.assign(new StructureSchema(), { name, namespace, traits, memberNames, memberList, }); class ErrorSchema extends StructureSchema { static symbol = Symbol.for("@smithy/err"); ctor; symbol = ErrorSchema.symbol; } const error = (namespace, name, traits, memberNames, memberList, ctor) => Schema.assign(new ErrorSchema(), { name, namespace, traits, memberNames, memberList, ctor: null, }); function translateTraits(indicator) { if (typeof indicator === "object") { return indicator; } indicator = indicator | 0; const traits = {}; let i = 0; for (const trait of [ "httpLabel", "idempotent", "idempotencyToken", "sensitive", "httpPayload", "httpResponseCode", "httpQueryParams", ]) { if (((indicator >> i++) & 1) === 1) { traits[trait] = 1; } } return traits; } const anno = { it: Symbol.for("@smithy/nor-struct-it"), }; class NormalizedSchema { ref; memberName; static symbol = Symbol.for("@smithy/nor"); symbol = NormalizedSchema.symbol; name; schema; _isMemberSchema; traits; memberTraits; normalizedTraits; constructor(ref, memberName) { this.ref = ref; this.memberName = memberName; const traitStack = []; let _ref = ref; let schema = ref; this._isMemberSchema = false; while (isMemberSchema(_ref)) { traitStack.push(_ref[1]); _ref = _ref[0]; schema = deref(_ref); this._isMemberSchema = true; } if (traitStack.length > 0) { this.memberTraits = {}; for (let i = traitStack.length - 1; i >= 0; --i) { const traitSet = traitStack[i]; Object.assign(this.memberTraits, translateTraits(traitSet)); } } else { this.memberTraits = 0; } if (schema instanceof NormalizedSchema) { const computedMemberTraits = this.memberTraits; Object.assign(this, schema); this.memberTraits = Object.assign({}, computedMemberTraits, schema.getMemberTraits(), this.getMemberTraits()); this.normalizedTraits = void 0; this.memberName = memberName ?? schema.memberName; return; } this.schema = deref(schema); if (isStaticSchema(this.schema)) { this.name = `${this.schema[1]}#${this.schema[2]}`; this.traits = this.schema[3]; } else { this.name = this.memberName ?? String(schema); this.traits = 0; } if (this._isMemberSchema && !memberName) { throw new Error(`@smithy/core/schema - NormalizedSchema member init ${this.getName(true)} missing member name.`); } } static [Symbol.hasInstance](lhs) { const isPrototype = this.prototype.isPrototypeOf(lhs); if (!isPrototype && typeof lhs === "object" && lhs !== null) { const ns = lhs; return ns.symbol === this.symbol; } return isPrototype; } static of(ref) { const sc = deref(ref); if (sc instanceof NormalizedSchema) { return sc; } if (isMemberSchema(sc)) { const [ns, traits] = sc; if (ns instanceof NormalizedSchema) { Object.assign(ns.getMergedTraits(), translateTraits(traits)); return ns; } throw new Error(`@smithy/core/schema - may not init unwrapped member schema=${JSON.stringify(ref, null, 2)}.`); } return new NormalizedSchema(sc); } getSchema() { const sc = this.schema; if (Array.isArray(sc) && sc[0] === 0) { return sc[4]; } return sc; } getName(withNamespace = false) { const { name } = this; const short = !withNamespace && name && name.includes("#"); return short ? name.split("#")[1] : name || undefined; } getMemberName() { return this.memberName; } isMemberSchema() { return this._isMemberSchema; } isListSchema() { const sc = this.getSchema(); return typeof sc === "number" ? sc >= 64 && sc < 128 : sc[0] === 1; } isMapSchema() { const sc = this.getSchema(); return typeof sc === "number" ? sc >= 128 && sc <= 0b1111_1111 : sc[0] === 2; } isStructSchema() { const sc = this.getSchema(); if (typeof sc !== "object") { return false; } const id = sc[0]; return (id === 3 || id === -3 || id === 4); } isUnionSchema() { const sc = this.getSchema(); if (typeof sc !== "object") { return false; } return sc[0] === 4; } isBlobSchema() { const sc = this.getSchema(); return sc === 21 || sc === 42; } isTimestampSchema() { const sc = this.getSchema(); return (typeof sc === "number" && sc >= 4 && sc <= 7); } isUnitSchema() { return this.getSchema() === "unit"; } isDocumentSchema() { return this.getSchema() === 15; } isStringSchema() { return this.getSchema() === 0; } isBooleanSchema() { return this.getSchema() === 2; } isNumericSchema() { return this.getSchema() === 1; } isBigIntegerSchema() { return this.getSchema() === 17; } isBigDecimalSchema() { return this.getSchema() === 19; } isStreaming() { const { streaming } = this.getMergedTraits(); return !!streaming || this.getSchema() === 42; } isIdempotencyToken() { return !!this.getMergedTraits().idempotencyToken; } getMergedTraits() { return (this.normalizedTraits ?? (this.normalizedTraits = { ...this.getOwnTraits(), ...this.getMemberTraits(), })); } getMemberTraits() { return translateTraits(this.memberTraits); } getOwnTraits() { return translateTraits(this.traits); } getKeySchema() { const [isDoc, isMap] = [this.isDocumentSchema(), this.isMapSchema()]; if (!isDoc && !isMap) { throw new Error(`@smithy/core/schema - cannot get key for non-map: ${this.getName(true)}`); } const schema = this.getSchema(); const memberSchema = isDoc ? 15 : schema[4] ?? 0; return member([memberSchema, 0], "key"); } getValueSchema() { const sc = this.getSchema(); const [isDoc, isMap, isList] = [this.isDocumentSchema(), this.isMapSchema(), this.isListSchema()]; const memberSchema = typeof sc === "number" ? 0b0011_1111 & sc : sc && typeof sc === "object" && (isMap || isList) ? sc[3 + sc[0]] : isDoc ? 15 : void 0; if (memberSchema != null) { return member([memberSchema, 0], isMap ? "value" : "member"); } throw new Error(`@smithy/core/schema - ${this.getName(true)} has no value member.`); } getMemberSchema(memberName) { const struct = this.getSchema(); if (this.isStructSchema() && struct[4].includes(memberName)) { const i = struct[4].indexOf(memberName); const memberSchema = struct[5][i]; return member(isMemberSchema(memberSchema) ? memberSchema : [memberSchema, 0], memberName); } if (this.isDocumentSchema()) { return member([15, 0], memberName); } throw new Error(`@smithy/core/schema - ${this.getName(true)} has no no member=${memberName}.`); } getMemberSchemas() { const buffer = {}; try { for (const [k, v] of this.structIterator()) { buffer[k] = v; } } catch (ignored) { } return buffer; } getEventStreamMember() { if (this.isStructSchema()) { for (const [memberName, memberSchema] of this.structIterator()) { if (memberSchema.isStreaming() && memberSchema.isStructSchema()) { return memberName; } } } return ""; } *structIterator() { if (this.isUnitSchema()) { return; } if (!this.isStructSchema()) { throw new Error("@smithy/core/schema - cannot iterate non-struct schema."); } const struct = this.getSchema(); const z = struct[4].length; let it = struct[anno.it]; if (it && z === it.length) { yield* it; return; } it = Array(z); for (let i = 0; i < z; ++i) { const k = struct[4][i]; const v = member([struct[5][i], 0], k); yield (it[i] = [k, v]); } struct[anno.it] = it; } } function member(memberSchema, memberName) { if (memberSchema instanceof NormalizedSchema) { return Object.assign(memberSchema, { memberName, _isMemberSchema: true, }); } const internalCtorAccess = NormalizedSchema; return new internalCtorAccess(memberSchema, memberName); } const isMemberSchema = (sc) => Array.isArray(sc) && sc.length === 2; const isStaticSchema = (sc) => Array.isArray(sc) && sc.length >= 5; class SimpleSchema extends Schema { static symbol = Symbol.for("@smithy/sim"); name; schemaRef; traits; symbol = SimpleSchema.symbol; } const sim = (namespace, name, schemaRef, traits) => Schema.assign(new SimpleSchema(), { name, namespace, traits, schemaRef, }); const simAdapter = (namespace, name, traits, schemaRef) => Schema.assign(new SimpleSchema(), { name, namespace, traits, schemaRef, }); const SCHEMA = { BLOB: 0b0001_0101, STREAMING_BLOB: 0b0010_1010, BOOLEAN: 0b0000_0010, STRING: 0b0000_0000, NUMERIC: 0b0000_0001, BIG_INTEGER: 0b0001_0001, BIG_DECIMAL: 0b0001_0011, DOCUMENT: 0b0000_1111, TIMESTAMP_DEFAULT: 0b0000_0100, TIMESTAMP_DATE_TIME: 0b0000_0101, TIMESTAMP_HTTP_DATE: 0b0000_0110, TIMESTAMP_EPOCH_SECONDS: 0b0000_0111, LIST_MODIFIER: 0b0100_0000, MAP_MODIFIER: 0b1000_0000, }; class TypeRegistry { namespace; schemas; exceptions; static registries = new Map(); constructor(namespace, schemas = new Map(), exceptions = new Map()) { this.namespace = namespace; this.schemas = schemas; this.exceptions = exceptions; } static for(namespace) { if (!TypeRegistry.registries.has(namespace)) { TypeRegistry.registries.set(namespace, new TypeRegistry(namespace)); } return TypeRegistry.registries.get(namespace); } copyFrom(other) { const { schemas, exceptions } = this; for (const [k, v] of other.schemas) { if (!schemas.has(k)) { schemas.set(k, v); } } for (const [k, v] of other.exceptions) { if (!exceptions.has(k)) { exceptions.set(k, v); } } } register(shapeId, schema) { const qualifiedName = this.normalizeShapeId(shapeId); for (const r of [this, TypeRegistry.for(qualifiedName.split("#")[0])]) { r.schemas.set(qualifiedName, schema); } } getSchema(shapeId) { const id = this.normalizeShapeId(shapeId); if (!this.schemas.has(id)) { throw new Error(`@smithy/core/schema - schema not found for ${id}`); } return this.schemas.get(id); } registerError(es, ctor) { const $error = es; const ns = $error[1]; for (const r of [this, TypeRegistry.for(ns)]) { r.schemas.set(ns + "#" + $error[2], $error); r.exceptions.set($error, ctor); } } getErrorCtor(es) { const $error = es; if (this.exceptions.has($error)) { return this.exceptions.get($error); } const registry = TypeRegistry.for($error[1]); return registry.exceptions.get($error); } getBaseException() { for (const exceptionKey of this.exceptions.keys()) { if (Array.isArray(exceptionKey)) { const [, ns, name] = exceptionKey; const id = ns + "#" + name; if (id.startsWith("smithy.ts.sdk.synthetic.") && id.endsWith("ServiceException")) { return exceptionKey; } } } return undefined; } find(predicate) { return [...this.schemas.values()].find(predicate); } clear() { this.schemas.clear(); this.exceptions.clear(); } normalizeShapeId(shapeId) { if (shapeId.includes("#")) { return shapeId; } return this.namespace + "#" + shapeId; } } exports.ErrorSchema = ErrorSchema; exports.ListSchema = ListSchema; exports.MapSchema = MapSchema; exports.NormalizedSchema = NormalizedSchema; exports.OperationSchema = OperationSchema; exports.SCHEMA = SCHEMA; exports.Schema = Schema; exports.SimpleSchema = SimpleSchema; exports.StructureSchema = StructureSchema; exports.TypeRegistry = TypeRegistry; exports.deref = deref; exports.deserializerMiddlewareOption = deserializerMiddlewareOption; exports.error = error; exports.getSchemaSerdePlugin = getSchemaSerdePlugin; exports.isStaticSchema = isStaticSchema; exports.list = list; exports.map = map; exports.op = op; exports.operation = operation; exports.serializerMiddlewareOption = serializerMiddlewareOption; exports.sim = sim; exports.simAdapter = simAdapter; exports.struct = struct; exports.translateTraits = translateTraits;