@aws-amplify/api-rest 3.5.6-unstable.7762f1a.0 → 4.0.0

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.
Files changed (147) hide show
  1. package/README.md +3 -0
  2. package/internals/package.json +8 -0
  3. package/internals/server/package.json +8 -0
  4. package/lib/apis/common/handler.d.ts +27 -0
  5. package/lib/apis/common/handler.js +73 -0
  6. package/lib/apis/common/internalPost.d.ts +16 -0
  7. package/lib/apis/common/internalPost.js +65 -0
  8. package/lib/apis/common/publicApis.d.ts +8 -0
  9. package/lib/apis/common/publicApis.js +44 -0
  10. package/lib/apis/index.d.ts +203 -0
  11. package/lib/apis/index.js +215 -0
  12. package/lib/apis/server.d.ts +151 -0
  13. package/lib/apis/server.js +162 -0
  14. package/lib/errors/CanceledError.d.ts +17 -0
  15. package/lib/errors/CanceledError.js +32 -0
  16. package/lib/errors/RestApiError.d.ts +4 -0
  17. package/lib/errors/RestApiError.js +15 -0
  18. package/lib/errors/assertValidatonError.d.ts +5 -0
  19. package/lib/errors/assertValidatonError.js +17 -0
  20. package/lib/errors/index.d.ts +4 -0
  21. package/lib/errors/index.js +15 -0
  22. package/lib/errors/validation.d.ts +6 -0
  23. package/lib/errors/validation.js +19 -0
  24. package/lib/index.d.ts +2 -2
  25. package/lib/index.js +10 -6
  26. package/lib/internals/index.d.ts +19 -0
  27. package/lib/internals/index.js +30 -0
  28. package/lib/internals/server.d.ts +20 -0
  29. package/lib/internals/server.js +30 -0
  30. package/lib/server.d.ts +2 -0
  31. package/lib/server.js +14 -0
  32. package/lib/tsconfig.tsbuildinfo +1 -0
  33. package/lib/types/index.d.ts +90 -37
  34. package/lib/types/index.js +0 -23
  35. package/lib/utils/constants.d.ts +8 -0
  36. package/lib/utils/constants.js +13 -0
  37. package/lib/utils/createCancellableOperation.d.ts +12 -0
  38. package/lib/utils/createCancellableOperation.js +63 -0
  39. package/lib/utils/index.d.ts +6 -0
  40. package/lib/utils/index.js +17 -0
  41. package/lib/utils/logger.d.ts +2 -0
  42. package/lib/utils/logger.js +7 -0
  43. package/lib/utils/normalizeHeaders.d.ts +1 -0
  44. package/lib/utils/normalizeHeaders.js +13 -0
  45. package/lib/utils/parseSigningInfo.d.ts +14 -0
  46. package/lib/utils/parseSigningInfo.js +41 -0
  47. package/lib/utils/resolveApiUrl.d.ts +12 -0
  48. package/lib/utils/resolveApiUrl.js +40 -0
  49. package/lib/utils/resolveCredentials.d.ts +5 -0
  50. package/lib/utils/resolveCredentials.js +15 -0
  51. package/lib/utils/serviceError.d.ts +10 -0
  52. package/lib/utils/serviceError.js +30 -0
  53. package/lib-esm/apis/common/handler.d.ts +27 -0
  54. package/lib-esm/apis/common/handler.js +69 -0
  55. package/lib-esm/apis/common/internalPost.d.ts +16 -0
  56. package/lib-esm/apis/common/internalPost.js +59 -0
  57. package/lib-esm/apis/common/publicApis.d.ts +8 -0
  58. package/lib-esm/apis/common/publicApis.js +35 -0
  59. package/lib-esm/apis/index.d.ts +203 -0
  60. package/lib-esm/apis/index.js +206 -0
  61. package/lib-esm/apis/server.d.ts +151 -0
  62. package/lib-esm/apis/server.js +153 -0
  63. package/lib-esm/errors/CanceledError.d.ts +17 -0
  64. package/lib-esm/errors/CanceledError.js +27 -0
  65. package/lib-esm/errors/RestApiError.d.ts +4 -0
  66. package/lib-esm/errors/RestApiError.js +11 -0
  67. package/lib-esm/errors/assertValidatonError.d.ts +5 -0
  68. package/lib-esm/errors/assertValidatonError.js +13 -0
  69. package/lib-esm/errors/index.d.ts +4 -0
  70. package/lib-esm/errors/index.js +6 -0
  71. package/lib-esm/errors/validation.d.ts +6 -0
  72. package/lib-esm/errors/validation.js +16 -0
  73. package/lib-esm/index.d.ts +2 -2
  74. package/lib-esm/index.js +2 -3
  75. package/lib-esm/internals/index.d.ts +19 -0
  76. package/lib-esm/internals/index.js +24 -0
  77. package/lib-esm/internals/server.d.ts +20 -0
  78. package/lib-esm/internals/server.js +24 -0
  79. package/lib-esm/server.d.ts +2 -0
  80. package/lib-esm/server.js +4 -0
  81. package/lib-esm/tsconfig.tsbuildinfo +1 -0
  82. package/lib-esm/types/index.d.ts +90 -37
  83. package/lib-esm/types/index.js +1 -23
  84. package/lib-esm/utils/constants.d.ts +8 -0
  85. package/lib-esm/utils/constants.js +10 -0
  86. package/lib-esm/utils/createCancellableOperation.d.ts +12 -0
  87. package/lib-esm/utils/createCancellableOperation.js +59 -0
  88. package/lib-esm/utils/index.d.ts +6 -0
  89. package/lib-esm/utils/index.js +8 -0
  90. package/lib-esm/utils/logger.d.ts +2 -0
  91. package/lib-esm/utils/logger.js +4 -0
  92. package/lib-esm/utils/normalizeHeaders.d.ts +1 -0
  93. package/lib-esm/utils/normalizeHeaders.js +9 -0
  94. package/lib-esm/utils/parseSigningInfo.d.ts +14 -0
  95. package/lib-esm/utils/parseSigningInfo.js +37 -0
  96. package/lib-esm/utils/resolveApiUrl.d.ts +12 -0
  97. package/lib-esm/utils/resolveApiUrl.js +36 -0
  98. package/lib-esm/utils/resolveCredentials.d.ts +5 -0
  99. package/lib-esm/utils/resolveCredentials.js +11 -0
  100. package/lib-esm/utils/serviceError.d.ts +10 -0
  101. package/lib-esm/utils/serviceError.js +25 -0
  102. package/package.json +113 -105
  103. package/server/package.json +8 -0
  104. package/src/apis/common/handler.ts +109 -0
  105. package/src/apis/common/internalPost.ts +81 -0
  106. package/src/apis/common/publicApis.ts +99 -0
  107. package/src/apis/index.ts +239 -0
  108. package/src/apis/server.ts +209 -0
  109. package/src/errors/CanceledError.ts +33 -0
  110. package/src/errors/RestApiError.ts +17 -0
  111. package/src/errors/assertValidatonError.ts +19 -0
  112. package/src/errors/index.ts +7 -0
  113. package/src/errors/validation.ts +20 -0
  114. package/src/index.ts +2 -2
  115. package/src/internals/index.ts +31 -0
  116. package/src/internals/server.ts +37 -0
  117. package/src/server.ts +5 -0
  118. package/src/types/index.ts +95 -44
  119. package/src/utils/constants.ts +15 -0
  120. package/src/utils/createCancellableOperation.ts +94 -0
  121. package/src/utils/index.ts +9 -0
  122. package/src/utils/logger.ts +6 -0
  123. package/src/utils/normalizeHeaders.ts +10 -0
  124. package/src/utils/parseSigningInfo.ts +52 -0
  125. package/src/utils/resolveApiUrl.ts +51 -0
  126. package/src/utils/resolveCredentials.ts +17 -0
  127. package/src/utils/serviceError.ts +35 -0
  128. package/lib/.tsbuildinfo +0 -3
  129. package/lib/RestAPI.d.ts +0 -108
  130. package/lib/RestAPI.js +0 -282
  131. package/lib/RestAPI.js.map +0 -1
  132. package/lib/RestClient.d.ts +0 -138
  133. package/lib/RestClient.js +0 -368
  134. package/lib/RestClient.js.map +0 -1
  135. package/lib/index.js.map +0 -1
  136. package/lib/types/index.js.map +0 -1
  137. package/lib-esm/.tsbuildinfo +0 -3
  138. package/lib-esm/RestAPI.d.ts +0 -108
  139. package/lib-esm/RestAPI.js +0 -280
  140. package/lib-esm/RestAPI.js.map +0 -1
  141. package/lib-esm/RestClient.d.ts +0 -138
  142. package/lib-esm/RestClient.js +0 -366
  143. package/lib-esm/RestClient.js.map +0 -1
  144. package/lib-esm/index.js.map +0 -1
  145. package/lib-esm/types/index.js.map +0 -1
  146. package/src/RestAPI.ts +0 -338
  147. package/src/RestClient.ts +0 -417
@@ -0,0 +1,4 @@
1
+ // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ // SPDX-License-Identifier: Apache-2.0
3
+ import { ConsoleLogger } from '@aws-amplify/core';
4
+ export const logger = new ConsoleLogger('RestApis');
@@ -0,0 +1 @@
1
+ export declare const normalizeHeaders: (headers?: Record<string, string>) => Record<string, string>;
@@ -0,0 +1,9 @@
1
+ // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ // SPDX-License-Identifier: Apache-2.0
3
+ export const normalizeHeaders = (headers) => {
4
+ const normalizedHeaders = {};
5
+ for (const key in headers) {
6
+ normalizedHeaders[key.toLowerCase()] = headers[key];
7
+ }
8
+ return normalizedHeaders;
9
+ };
@@ -0,0 +1,14 @@
1
+ import { AmplifyClassV6 } from '@aws-amplify/core';
2
+ /**
3
+ * Infer the signing service and region from the given URL, and for REST API only, from the Amplify configuration.
4
+ * It supports raw API Gateway endpoint and AppSync endpoint.
5
+ *
6
+ * @internal
7
+ */
8
+ export declare const parseSigningInfo: (url: URL, restApiOptions?: {
9
+ amplify: AmplifyClassV6;
10
+ apiName: string;
11
+ }) => {
12
+ service: string;
13
+ region: string;
14
+ };
@@ -0,0 +1,37 @@
1
+ // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ // SPDX-License-Identifier: Apache-2.0
3
+ import { APIG_HOSTNAME_PATTERN, DEFAULT_IAM_SIGNING_REGION, DEFAULT_REST_IAM_SIGNING_SERVICE, } from './constants';
4
+ /**
5
+ * Infer the signing service and region from the given URL, and for REST API only, from the Amplify configuration.
6
+ * It supports raw API Gateway endpoint and AppSync endpoint.
7
+ *
8
+ * @internal
9
+ */
10
+ export const parseSigningInfo = (url, restApiOptions) => {
11
+ const { service: signingService = DEFAULT_REST_IAM_SIGNING_SERVICE, region: signingRegion = DEFAULT_IAM_SIGNING_REGION, } = restApiOptions?.amplify.getConfig()?.API?.REST?.[restApiOptions?.apiName] ??
12
+ {};
13
+ const { hostname } = url;
14
+ const [, service, region] = APIG_HOSTNAME_PATTERN.exec(hostname) ?? [];
15
+ if (service === DEFAULT_REST_IAM_SIGNING_SERVICE) {
16
+ // The configured endpoint is an API Gateway endpoint
17
+ // @see: https://docs.aws.amazon.com/apigateway/latest/developerguide/how-to-call-api.html
18
+ return {
19
+ service,
20
+ region: region ?? signingRegion,
21
+ };
22
+ }
23
+ else if (service === 'appsync-api') {
24
+ // AppSync endpoint is internally supported because GraphQL operation will send request using POST handler.
25
+ // example: https://xxxx.appsync-api.us-east-1.amazonaws.com/graphql
26
+ return {
27
+ service: 'appsync',
28
+ region: region ?? signingRegion,
29
+ };
30
+ }
31
+ else {
32
+ return {
33
+ service: signingService,
34
+ region: signingRegion,
35
+ };
36
+ }
37
+ };
@@ -0,0 +1,12 @@
1
+ import { AmplifyClassV6 } from '@aws-amplify/core';
2
+ /**
3
+ * Resolve the REST API request URL by:
4
+ * 1. Loading the REST API endpoint from the Amplify configuration with corresponding API name.
5
+ * 2. Appending the path to the endpoint.
6
+ * 3. Merge the query parameters from path and the queryParameter argument which is taken from the public REST API
7
+ * options.
8
+ * 4. Validating the resulting URL string.
9
+ *
10
+ * @internal
11
+ */
12
+ export declare const resolveApiUrl: (amplify: AmplifyClassV6, apiName: string, path: string, queryParams?: Record<string, string>) => URL;
@@ -0,0 +1,36 @@
1
+ // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ // SPDX-License-Identifier: Apache-2.0
3
+ import { AmplifyUrl, AmplifyUrlSearchParams, } from '@aws-amplify/core/internals/utils';
4
+ import { RestApiError, RestApiValidationErrorCode, assertValidationError, validationErrorMap, } from '../errors';
5
+ /**
6
+ * Resolve the REST API request URL by:
7
+ * 1. Loading the REST API endpoint from the Amplify configuration with corresponding API name.
8
+ * 2. Appending the path to the endpoint.
9
+ * 3. Merge the query parameters from path and the queryParameter argument which is taken from the public REST API
10
+ * options.
11
+ * 4. Validating the resulting URL string.
12
+ *
13
+ * @internal
14
+ */
15
+ export const resolveApiUrl = (amplify, apiName, path, queryParams) => {
16
+ const urlStr = amplify.getConfig()?.API?.REST?.[apiName]?.endpoint;
17
+ assertValidationError(!!urlStr, RestApiValidationErrorCode.InvalidApiName);
18
+ try {
19
+ const url = new AmplifyUrl(urlStr + path);
20
+ if (queryParams) {
21
+ const mergedQueryParams = new AmplifyUrlSearchParams(url.searchParams);
22
+ Object.entries(queryParams).forEach(([key, value]) => {
23
+ mergedQueryParams.set(key, value);
24
+ });
25
+ url.search = new AmplifyUrlSearchParams(mergedQueryParams).toString();
26
+ }
27
+ return url;
28
+ }
29
+ catch (error) {
30
+ throw new RestApiError({
31
+ name: RestApiValidationErrorCode.InvalidApiName,
32
+ ...validationErrorMap[RestApiValidationErrorCode.InvalidApiName],
33
+ recoverySuggestion: `Please make sure the REST endpoint URL is a valid URL string. Got ${urlStr}`,
34
+ });
35
+ }
36
+ };
@@ -0,0 +1,5 @@
1
+ import { AmplifyClassV6 } from '@aws-amplify/core';
2
+ /**
3
+ * @internal
4
+ */
5
+ export declare const resolveCredentials: (amplify: AmplifyClassV6) => Promise<import("@aws-amplify/core/lib-esm/libraryUtils").AWSCredentials>;
@@ -0,0 +1,11 @@
1
+ // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ // SPDX-License-Identifier: Apache-2.0
3
+ import { RestApiValidationErrorCode, assertValidationError } from '../errors';
4
+ /**
5
+ * @internal
6
+ */
7
+ export const resolveCredentials = async (amplify) => {
8
+ const { credentials } = await amplify.Auth.fetchAuthSession();
9
+ assertValidationError(!!credentials && !!credentials.accessKeyId && !!credentials.secretAccessKey, RestApiValidationErrorCode.NoCredentials);
10
+ return credentials;
11
+ };
@@ -0,0 +1,10 @@
1
+ import { MetadataBearer } from '@aws-sdk/types';
2
+ import { HttpResponse } from '@aws-amplify/core/internals/aws-client-utils';
3
+ import { RestApiError } from '../errors';
4
+ /**
5
+ * Internal-only method to create a new RestApiError from a service error.
6
+ *
7
+ * @internal
8
+ */
9
+ export declare const buildRestApiServiceError: (error: Error) => RestApiError;
10
+ export declare const parseRestApiServiceError: (response?: HttpResponse) => Promise<(RestApiError & MetadataBearer) | undefined>;
@@ -0,0 +1,25 @@
1
+ import { parseJsonError, } from '@aws-amplify/core/internals/aws-client-utils';
2
+ import { RestApiError } from '../errors';
3
+ /**
4
+ * Internal-only method to create a new RestApiError from a service error.
5
+ *
6
+ * @internal
7
+ */
8
+ export const buildRestApiServiceError = (error) => {
9
+ const restApiError = new RestApiError({
10
+ name: error?.name,
11
+ message: error.message,
12
+ underlyingError: error,
13
+ });
14
+ return restApiError;
15
+ };
16
+ export const parseRestApiServiceError = async (response) => {
17
+ const parsedError = await parseJsonError(response);
18
+ if (!parsedError) {
19
+ // Response is not an error.
20
+ return;
21
+ }
22
+ return Object.assign(buildRestApiServiceError(parsedError), {
23
+ $metadata: parsedError.$metadata,
24
+ });
25
+ };
package/package.json CHANGED
@@ -1,107 +1,115 @@
1
1
  {
2
- "name": "@aws-amplify/api-rest",
3
- "version": "3.5.6-unstable.7762f1a.0+7762f1a",
4
- "description": "Api-rest category of aws-amplify",
5
- "main": "./lib/index.js",
6
- "module": "./lib-esm/index.js",
7
- "typings": "./lib-esm/index.d.ts",
8
- "react-native": {
9
- "./lib/index": "./lib-esm/index.js"
10
- },
11
- "sideEffects": [
12
- "./lib/RestAPI.js",
13
- "./lib-esm/RestAPI.js"
14
- ],
15
- "publishConfig": {
16
- "access": "public"
17
- },
18
- "scripts": {
19
- "test": "npm run lint && jest --coverage",
20
- "test:size": "size-limit",
21
- "build-with-test": "npm test && npm run build",
22
- "build:cjs": "node ./build es5 && webpack && webpack --config ./webpack.config.dev.js",
23
- "build:esm": "node ./build es6",
24
- "build:cjs:watch": "node ./build es5 --watch",
25
- "build:esm:watch": "node ./build es6 --watch",
26
- "build": "npm run clean && npm run build:esm && npm run build:cjs",
27
- "clean": "npm run clean:size && rimraf lib-esm lib dist",
28
- "clean:size": "rimraf dual-publish-tmp tmp*",
29
- "format": "echo \"Not implemented\"",
30
- "lint": "tslint 'src/**/*.ts' && npm run ts-coverage",
31
- "ts-coverage": "typescript-coverage-report -p ./tsconfig.build.json -t 65.41"
32
- },
33
- "repository": {
34
- "type": "git",
35
- "url": "https://github.com/aws-amplify/amplify-js.git"
36
- },
37
- "author": "Amazon Web Services",
38
- "license": "Apache-2.0",
39
- "bugs": {
40
- "url": "https://github.com/aws/aws-amplify/issues"
41
- },
42
- "homepage": "https://aws-amplify.github.io/",
43
- "files": [
44
- "lib",
45
- "lib-esm",
46
- "src"
47
- ],
48
- "dependencies": {
49
- "@aws-amplify/core": "5.8.6-unstable.7762f1a.0+7762f1a",
50
- "axios": "0.26.0",
51
- "tslib": "^1.8.0",
52
- "url": "0.11.0"
53
- },
54
- "size-limit": [
55
- {
56
- "name": "API (rest client)",
57
- "path": "./lib-esm/index.js",
58
- "import": "{ Amplify, RestAPI }",
59
- "limit": "31 kB"
60
- }
61
- ],
62
- "jest": {
63
- "globals": {
64
- "ts-jest": {
65
- "diagnostics": false,
66
- "tsConfig": {
67
- "lib": [
68
- "es5",
69
- "es2015",
70
- "dom",
71
- "esnext.asynciterable",
72
- "es2017.object"
73
- ],
74
- "allowJs": true
75
- }
76
- }
77
- },
78
- "transform": {
79
- "^.+\\.(js|jsx|ts|tsx)$": "ts-jest"
80
- },
81
- "testRegex": "(/__tests__/.*|\\.(test|spec))\\.(tsx?|jsx?)$",
82
- "moduleFileExtensions": [
83
- "ts",
84
- "tsx",
85
- "js",
86
- "json",
87
- "jsx"
88
- ],
89
- "testEnvironment": "jsdom",
90
- "testURL": "http://localhost/",
91
- "coverageThreshold": {
92
- "global": {
93
- "branches": 0,
94
- "functions": 0,
95
- "lines": 0,
96
- "statements": 0
97
- }
98
- },
99
- "coveragePathIgnorePatterns": [
100
- "/node_modules/",
101
- "dist",
102
- "lib",
103
- "lib-esm"
104
- ]
105
- },
106
- "gitHead": "7762f1a7076e622ec354c24539a3b57ce3ec4290"
2
+ "name": "@aws-amplify/api-rest",
3
+ "private": false,
4
+ "version": "4.0.0",
5
+ "description": "Api-rest category of aws-amplify",
6
+ "main": "./lib/index.js",
7
+ "module": "./lib-esm/index.js",
8
+ "typings": "./lib-esm/index.d.ts",
9
+ "react-native": {
10
+ "./lib/index": "./lib-esm/index.js"
11
+ },
12
+ "sideEffects": [
13
+ "./lib/RestAPI.js",
14
+ "./lib-esm/RestAPI.js"
15
+ ],
16
+ "publishConfig": {
17
+ "access": "public"
18
+ },
19
+ "scripts": {
20
+ "test": "npm run lint && jest -w 1 --coverage",
21
+ "test:watch": "tslint 'src/**/*.ts' && jest -w 1 --watch",
22
+ "build-with-test": "npm run clean && npm test && tsc && webpack",
23
+ "build:cjs": "rimraf lib && tsc -m commonjs --outDir lib && webpack && webpack --config ./webpack.config.dev.js",
24
+ "build:esm": "rimraf lib-esm && tsc -m esnext --outDir lib-esm",
25
+ "build:cjs:watch": "rimraf lib && tsc -m commonjs --outDir lib --watch",
26
+ "build:esm:watch": "rimraf lib-esm && tsc -m esnext --outDir lib-esm --watch",
27
+ "build": "npm run clean && npm run build:esm && npm run build:cjs",
28
+ "clean": "npm run clean:size && rimraf lib-esm lib dist",
29
+ "clean:size": "rimraf dual-publish-tmp tmp*",
30
+ "format": "echo \"Not implemented\"",
31
+ "lint": "tslint 'src/**/*.ts' && npm run ts-coverage",
32
+ "ts-coverage": "typescript-coverage-report -p ./tsconfig.json -t 70.0"
33
+ },
34
+ "repository": {
35
+ "type": "git",
36
+ "url": "https://github.com/aws-amplify/amplify-js.git"
37
+ },
38
+ "author": "Amazon Web Services",
39
+ "license": "Apache-2.0",
40
+ "bugs": {
41
+ "url": "https://github.com/aws/aws-amplify/issues"
42
+ },
43
+ "homepage": "https://aws-amplify.github.io/",
44
+ "files": [
45
+ "lib",
46
+ "lib-esm",
47
+ "src",
48
+ "internals",
49
+ "server"
50
+ ],
51
+ "dependencies": {
52
+ "tslib": "^2.5.0"
53
+ },
54
+ "peerDependencies": {
55
+ "@aws-amplify/core": "^6.0.0"
56
+ },
57
+ "devDependencies": {
58
+ "@aws-amplify/core": "6.0.0",
59
+ "@aws-amplify/react-native": "^1.0.0",
60
+ "typescript": "5.0.2"
61
+ },
62
+ "size-limit": [
63
+ {
64
+ "name": "API (rest client)",
65
+ "path": "./lib-esm/index.js",
66
+ "import": "{ Amplify, RestAPI }",
67
+ "limit": "31.5 kB"
68
+ }
69
+ ],
70
+ "jest": {
71
+ "globals": {
72
+ "ts-jest": {
73
+ "diagnostics": false,
74
+ "tsConfig": {
75
+ "allowJs": true,
76
+ "noEmitOnError": false
77
+ }
78
+ }
79
+ },
80
+ "transform": {
81
+ "^.+\\.(js|jsx|ts|tsx)$": "ts-jest"
82
+ },
83
+ "testPathIgnorePatterns": [
84
+ "/testUtils/"
85
+ ],
86
+ "testRegex": "(/__tests__/.*|\\.(test|spec))\\.(tsx?|jsx?)$",
87
+ "moduleFileExtensions": [
88
+ "ts",
89
+ "tsx",
90
+ "js",
91
+ "json",
92
+ "jsx"
93
+ ],
94
+ "testEnvironment": "jsdom",
95
+ "testURL": "http://localhost/",
96
+ "coverageThreshold": {
97
+ "global": {
98
+ "branches": 0,
99
+ "functions": 0,
100
+ "lines": 0,
101
+ "statements": 0
102
+ }
103
+ },
104
+ "coveragePathIgnorePatterns": [
105
+ "node_modules",
106
+ "dist",
107
+ "lib",
108
+ "lib-esm"
109
+ ],
110
+ "setupFiles": [
111
+ "<rootDir>/setupTests.ts"
112
+ ]
113
+ },
114
+ "gitHead": "d505105326d7f6214f6bd1e06eb20be3a3651377"
107
115
  }
@@ -0,0 +1,8 @@
1
+ {
2
+ "name": "@aws-amplify/api-rest/server",
3
+ "types": "../lib-esm/server.d.ts",
4
+ "main": "../lib/server.js",
5
+ "module": "../lib-esm/server.js",
6
+ "react-native": "../lib-esm/server.js",
7
+ "sideEffects": false
8
+ }
@@ -0,0 +1,109 @@
1
+ // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ // SPDX-License-Identifier: Apache-2.0
3
+ import { AmplifyClassV6 } from '@aws-amplify/core';
4
+ import {
5
+ HttpRequest,
6
+ unauthenticatedHandler,
7
+ Headers,
8
+ getRetryDecider,
9
+ jitteredBackoff,
10
+ authenticatedHandler,
11
+ } from '@aws-amplify/core/internals/aws-client-utils';
12
+ import { DocumentType } from '@aws-amplify/core/internals/utils';
13
+
14
+ import {
15
+ parseRestApiServiceError,
16
+ parseSigningInfo,
17
+ resolveCredentials,
18
+ } from '../../utils';
19
+ import { normalizeHeaders } from '../../utils/normalizeHeaders';
20
+ import { RestApiResponse } from '../../types';
21
+
22
+ type HandlerOptions = Omit<HttpRequest, 'body' | 'headers'> & {
23
+ body?: DocumentType | FormData;
24
+ headers?: Headers;
25
+ withCredentials?: boolean;
26
+ };
27
+
28
+ type SigningServiceInfo = {
29
+ service?: string;
30
+ region?: string;
31
+ };
32
+
33
+ /**
34
+ * Make REST API call with best-effort IAM auth.
35
+ * @param amplify Amplify instance to to resolve credentials and tokens. Should use different instance in client-side
36
+ * and SSR
37
+ * @param options Options accepted from public API options when calling the handlers.
38
+ * @param signingServiceInfo Internal-only options enable IAM auth as well as to to overwrite the IAM signing service
39
+ * and region. If specified, and NONE of API Key header or Auth header is present, IAM auth will be used.
40
+ *
41
+ * @internal
42
+ */
43
+ export const transferHandler = async (
44
+ amplify: AmplifyClassV6,
45
+ options: HandlerOptions & { abortSignal: AbortSignal },
46
+ signingServiceInfo?: SigningServiceInfo
47
+ ): Promise<RestApiResponse> => {
48
+ const { url, method, headers, body, withCredentials, abortSignal } = options;
49
+ const resolvedBody = body
50
+ ? body instanceof FormData
51
+ ? body
52
+ : JSON.stringify(body ?? '')
53
+ : undefined;
54
+ const resolvedHeaders: Headers = {
55
+ ...normalizeHeaders(headers),
56
+ ...(resolvedBody
57
+ ? {
58
+ 'content-type':
59
+ body instanceof FormData
60
+ ? 'multipart/form-data'
61
+ : 'application/json; charset=UTF-8',
62
+ }
63
+ : {}),
64
+ };
65
+ const request = {
66
+ url,
67
+ headers: resolvedHeaders,
68
+ method,
69
+ body: resolvedBody,
70
+ };
71
+ const baseOptions = {
72
+ retryDecider: getRetryDecider(parseRestApiServiceError),
73
+ computeDelay: jitteredBackoff,
74
+ withCrossDomainCredentials: withCredentials,
75
+ abortSignal,
76
+ };
77
+
78
+ const isIamAuthApplicable = iamAuthApplicable(request, signingServiceInfo);
79
+ let response: RestApiResponse;
80
+ if (isIamAuthApplicable) {
81
+ const signingInfoFromUrl = parseSigningInfo(url);
82
+ const signingService =
83
+ signingServiceInfo?.service ?? signingInfoFromUrl.service;
84
+ const signingRegion =
85
+ signingServiceInfo?.region ?? signingInfoFromUrl.region;
86
+ const credentials = await resolveCredentials(amplify);
87
+ response = await authenticatedHandler(request, {
88
+ ...baseOptions,
89
+ credentials,
90
+ region: signingRegion,
91
+ service: signingService,
92
+ });
93
+ } else {
94
+ response = await unauthenticatedHandler(request, {
95
+ ...baseOptions,
96
+ });
97
+ }
98
+ // Clean-up un-modeled properties from response.
99
+ return {
100
+ statusCode: response.statusCode,
101
+ headers: response.headers,
102
+ body: response.body,
103
+ };
104
+ };
105
+
106
+ const iamAuthApplicable = (
107
+ { headers }: HttpRequest,
108
+ signingServiceInfo?: SigningServiceInfo
109
+ ) => !headers.authorization && !headers['x-api-key'] && !!signingServiceInfo;
@@ -0,0 +1,81 @@
1
+ // Copyright Amazon.com, Inc. or its affiliates. All Rights Reserved.
2
+ // SPDX-License-Identifier: Apache-2.0
3
+
4
+ import { AmplifyClassV6 } from '@aws-amplify/core';
5
+
6
+ import { InternalPostInput, RestApiResponse } from '../../types';
7
+ import { transferHandler } from './handler';
8
+ import { createCancellableOperation } from '../../utils';
9
+
10
+ /**
11
+ * This weak map provides functionality to cancel a request given the promise containing the `post` request.
12
+ *
13
+ * 1. For every GraphQL POST request, an abort controller is created and supplied to the request.
14
+ * 2. The promise fulfilled by GraphGL POST request is then mapped to that abort controller.
15
+ * 3. The promise is returned to the external caller.
16
+ * 4. The caller can either wait for the promise to fulfill or call `cancel(promise)` to cancel the request.
17
+ * 5. If `cancel(promise)` is called, then the corresponding abort controller is retrieved from the map below.
18
+ * 6. GraphQL POST request will be rejected with the error message provided during cancel.
19
+ * 7. Caller can check if the error is because of cancelling by calling `isCancelError(error)`.
20
+ */
21
+ const cancelTokenMap = new WeakMap<Promise<any>, AbortController>();
22
+
23
+ /**
24
+ * @internal
25
+ */
26
+ export const post = (
27
+ amplify: AmplifyClassV6,
28
+ { url, options, abortController }: InternalPostInput
29
+ ): Promise<RestApiResponse> => {
30
+ const controller = abortController ?? new AbortController();
31
+ const responsePromise = createCancellableOperation(async () => {
32
+ const response = transferHandler(
33
+ amplify,
34
+ {
35
+ url,
36
+ method: 'POST',
37
+ ...options,
38
+ abortSignal: controller.signal,
39
+ },
40
+ options?.signingServiceInfo
41
+ );
42
+ return response;
43
+ }, controller);
44
+
45
+ const responseWithCleanUp = responsePromise.finally(() => {
46
+ cancelTokenMap.delete(responseWithCleanUp);
47
+ });
48
+ return responseWithCleanUp;
49
+ };
50
+
51
+ /**
52
+ * Cancels a request given the promise returned by `post`.
53
+ * If the request is already completed, this function does nothing.
54
+ * It MUST be used after `updateRequestToBeCancellable` is called.
55
+ */
56
+ export const cancel = (
57
+ promise: Promise<RestApiResponse>,
58
+ message?: string
59
+ ): boolean => {
60
+ const controller = cancelTokenMap.get(promise);
61
+ if (controller) {
62
+ controller.abort(message);
63
+ if (message && controller.signal.reason !== message) {
64
+ // In runtimes where `AbortSignal.reason` is not supported, we track the reason ourselves.
65
+ // @ts-expect-error reason is read-only property.
66
+ controller.signal['reason'] = message;
67
+ }
68
+ return true;
69
+ }
70
+ return false;
71
+ };
72
+
73
+ /**
74
+ * MUST be used to make a promise including internal `post` API call cancellable.
75
+ */
76
+ export const updateRequestToBeCancellable = (
77
+ promise: Promise<any>,
78
+ controller: AbortController
79
+ ) => {
80
+ cancelTokenMap.set(promise, controller);
81
+ };