@jentic/arazzo-resolver 1.0.0-alpha.24 → 1.0.0-alpha.25

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.
package/CHANGELOG.md CHANGED
@@ -3,6 +3,12 @@
3
3
  All notable changes to this project will be documented in this file.
4
4
  See [Conventional Commits](https://conventionalcommits.org) for commit guidelines.
5
5
 
6
+ # [1.0.0-alpha.25](https://github.com/jentic/jentic-arazzo-tools/compare/v1.0.0-alpha.24...v1.0.0-alpha.25) (2026-03-11)
7
+
8
+ ### Bug Fixes
9
+
10
+ - **release:** fix issue in lerna not publishing _.cjs|_.mjs files ([8982184](https://github.com/jentic/jentic-arazzo-tools/commit/8982184ddae167b6f2a772114f9a9321f3b67d14))
11
+
6
12
  # [1.0.0-alpha.24](https://github.com/jentic/jentic-arazzo-tools/compare/v1.0.0-alpha.23...v1.0.0-alpha.24) (2026-03-11)
7
13
 
8
14
  **Note:** Version bump only for package @jentic/arazzo-resolver
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@jentic/arazzo-resolver",
3
- "version": "1.0.0-alpha.24",
3
+ "version": "1.0.0-alpha.25",
4
4
  "description": "Resolver for Arazzo Documents.",
5
5
  "keywords": [
6
6
  "arazzo",
@@ -49,7 +49,7 @@
49
49
  "license": "Apache-2.0",
50
50
  "dependencies": {
51
51
  "@babel/runtime-corejs3": "^7.28.4",
52
- "@jentic/arazzo-parser": "1.0.0-alpha.24",
52
+ "@jentic/arazzo-parser": "1.0.0-alpha.25",
53
53
  "@speclynx/apidom-datamodel": "^4.0.3",
54
54
  "@speclynx/apidom-error": "^4.0.3",
55
55
  "@speclynx/apidom-ns-arazzo-1": "^4.0.3",
@@ -63,8 +63,7 @@
63
63
  "@speclynx/apidom-core": "^4.0.3"
64
64
  },
65
65
  "files": [
66
- "src/**/*.mjs",
67
- "src/**/*.cjs",
66
+ "src/",
68
67
  "dist/",
69
68
  "types/arazzo-resolver.d.ts",
70
69
  "LICENSE",
@@ -72,5 +71,5 @@
72
71
  "README.md",
73
72
  "CHANGELOG.md"
74
73
  ],
75
- "gitHead": "4d69c9a6c690d8fac8938c7032f57258948d76ce"
74
+ "gitHead": "b9a3213b0561fc58e0491c7e638d6a96383befff"
76
75
  }
@@ -0,0 +1,231 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime-corejs3/helpers/interopRequireDefault").default;
4
+ exports.__esModule = true;
5
+ exports.defaultOptions = void 0;
6
+ exports.dereference = dereference;
7
+ exports.dereferenceElement = dereferenceElement;
8
+ var _apidomDatamodel = require("@speclynx/apidom-datamodel");
9
+ var _empty = require("@speclynx/apidom-reference/configuration/empty");
10
+ var _arazzo = _interopRequireDefault(require("@speclynx/apidom-reference/dereference/strategies/arazzo-1"));
11
+ var _openapi = _interopRequireDefault(require("@speclynx/apidom-reference/dereference/strategies/openapi-2"));
12
+ var _openapi2 = _interopRequireDefault(require("@speclynx/apidom-reference/dereference/strategies/openapi-3-0"));
13
+ var _openapi3 = _interopRequireDefault(require("@speclynx/apidom-reference/dereference/strategies/openapi-3-1"));
14
+ var _json = _interopRequireDefault(require("@speclynx/apidom-reference/parse/parsers/json"));
15
+ var _yaml = _interopRequireDefault(require("@speclynx/apidom-reference/parse/parsers/yaml-1-2"));
16
+ var _binary = _interopRequireDefault(require("@speclynx/apidom-reference/parse/parsers/binary"));
17
+ var _apidomNsArazzo = require("@speclynx/apidom-ns-arazzo-1");
18
+ var _arazzoParser = require("@jentic/arazzo-parser");
19
+ var _DereferenceError = _interopRequireDefault(require("../errors/DereferenceError.cjs"));
20
+ /**
21
+ * Options for dereferencing Arazzo Documents.
22
+ * @public
23
+ */
24
+
25
+ /**
26
+ * Default reference options for dereferencing Arazzo Documents.
27
+ * @public
28
+ */
29
+ const defaultOptions = exports.defaultOptions = {
30
+ resolve: {
31
+ resolvers: [..._arazzoParser.defaultArazzoOptions.resolve.resolvers]
32
+ },
33
+ parse: {
34
+ parsers: [..._arazzoParser.defaultArazzoOptions.parse.parsers, new _json.default({
35
+ allowEmpty: false
36
+ }), new _yaml.default({
37
+ allowEmpty: false
38
+ }), new _binary.default({
39
+ allowEmpty: false
40
+ })],
41
+ parserOpts: {
42
+ ..._arazzoParser.defaultArazzoOptions.parse.parserOpts
43
+ }
44
+ },
45
+ dereference: {
46
+ strategies: [new _arazzo.default(), new _openapi.default(), new _openapi2.default(), new _openapi3.default()],
47
+ strategyOpts: {
48
+ sourceDescriptions: false
49
+ }
50
+ }
51
+ };
52
+
53
+ /**
54
+ * Dereferences an Arazzo Document from a file system path or HTTP(S) URL.
55
+ *
56
+ * This function resolves all JSON References ($ref) and Reusable Object references
57
+ * ($components.*) in the Arazzo Document.
58
+ *
59
+ * Source descriptions can optionally be dereferenced using strategy options:
60
+ * - `sourceDescriptions`: `true` (all) or `['name1', 'name2']` (specific names only)
61
+ * - `sourceDescriptionsMaxDepth`: Maximum recursion depth for nested Arazzo source descriptions (default: `+Infinity`)
62
+ *
63
+ * Options can be passed globally via `strategyOpts` or strategy-specific via `strategyOpts['arazzo-1']`.
64
+ *
65
+ * @param uri - A file system path or HTTP(S) URL to the Arazzo Document
66
+ * @param options - Reference options (uses defaultOptions when not provided)
67
+ * @returns A promise that resolves to the dereferenced Arazzo Document as ApiDOM element
68
+ * @throws DereferenceError - When dereferencing fails or document is not an Arazzo specification. The original error is available via the `cause` property.
69
+ *
70
+ * @example
71
+ * // Dereference from file
72
+ * const result = await dereferenceArazzo('/path/to/arazzo.json');
73
+ *
74
+ * @example
75
+ * // Dereference from URL
76
+ * const result = await dereferenceArazzo('https://example.com/arazzo.yaml');
77
+ *
78
+ * @example
79
+ * Dereference with source descriptions
80
+ * ```typescript
81
+ * const result = await dereferenceArazzo('/path/to/arazzo.json', {
82
+ * dereference: { strategyOpts: { sourceDescriptions: true } },
83
+ * });
84
+ * ```
85
+ *
86
+ * @example
87
+ * // Dereference with custom options
88
+ * const result = await dereferenceArazzo('/path/to/arazzo.json', customReferenceOptions);
89
+ * @public
90
+ */
91
+ async function dereference(uri, options = {}) {
92
+ const mergedOptions = (0, _empty.mergeOptions)(defaultOptions, options);
93
+ try {
94
+ const parseResult = await (0, _empty.dereference)(uri, mergedOptions);
95
+
96
+ // validate that the dereferenced document is an Arazzo specification
97
+ if (!(0, _apidomNsArazzo.isArazzoSpecification1Element)(parseResult.api)) {
98
+ throw new _empty.UnmatchedDereferenceStrategyError(`Could not find a dereference strategy that can dereference "${uri}" as an Arazzo specification`);
99
+ }
100
+ parseResult.meta.set('retrievalURI', uri);
101
+ return parseResult;
102
+ } catch (error) {
103
+ throw new _DereferenceError.default(`Failed to dereference Arazzo Document at "${uri}"`, {
104
+ cause: error
105
+ });
106
+ }
107
+ }
108
+
109
+ /**
110
+ * Dereferences an ApiDOM element representing an Arazzo Document.
111
+ *
112
+ * This function resolves all JSON References ($ref) and Reusable Object references
113
+ * ($components.*) in the Arazzo Document element.
114
+ *
115
+ * Supported scenarios:
116
+ * - ParseResultElement with retrievalURI metadata: baseURI derived automatically
117
+ * - ParseResultElement without retrievalURI: requires `options.resolve.baseURI`
118
+ * - Child element (e.g., WorkflowElement) with parseResult in strategyOpts:
119
+ * requires `options.dereference.strategyOpts.parseResult` for component resolution,
120
+ * and `options.resolve.baseURI` if parseResult lacks retrievalURI metadata
121
+ *
122
+ * Source descriptions can optionally be dereferenced using strategy options:
123
+ * - `sourceDescriptions`: `true` (all) or `['name1', 'name2']` (specific names only)
124
+ * - `sourceDescriptionsMaxDepth`: Maximum recursion depth for nested Arazzo source descriptions (default: `+Infinity`)
125
+ *
126
+ * Options can be passed globally via `strategyOpts` or strategy-specific via `strategyOpts['arazzo-1']`.
127
+ *
128
+ * @param element - An ApiDOM element (ParseResultElement or child element like WorkflowElement)
129
+ * @param options - Reference options (uses defaultOptions when not provided)
130
+ * @returns A promise that resolves to the dereferenced element
131
+ * @throws DereferenceError - When baseURI is required but not provided, or when dereferencing fails
132
+ *
133
+ * @example
134
+ * Dereference ParseResultElement with retrievalURI (from file parsing)
135
+ * ```typescript
136
+ * import { parseArazzo } from '@jentic/arazzo-parser';
137
+ *
138
+ * const parseResult = await parseArazzo('/path/to/arazzo.json');
139
+ * const dereferenced = await dereferenceArazzoElement(parseResult);
140
+ * ```
141
+ *
142
+ * @example
143
+ * Dereference ParseResultElement without retrievalURI (from inline parsing)
144
+ * ```typescript
145
+ * const parseResult = await parseArazzo({ arazzo: '1.0.1', ... });
146
+ * const dereferenced = await dereferenceArazzoElement(parseResult, {
147
+ * resolve: { baseURI: 'https://example.com/arazzo.json' },
148
+ * });
149
+ * ```
150
+ *
151
+ * @example
152
+ * Dereference child element (e.g., WorkflowElement)
153
+ * ```typescript
154
+ * const parseResult = await parseArazzo('/path/to/arazzo.json');
155
+ * const workflow = parseResult.api.workflows.get(0);
156
+ * const dereferenced = await dereferenceArazzoElement(workflow, {
157
+ * dereference: { strategyOpts: { parseResult } },
158
+ * });
159
+ * ```
160
+ *
161
+ * @example
162
+ * Dereference with source descriptions
163
+ * ```typescript
164
+ * const parseResult = await parseArazzo('/path/to/arazzo.json');
165
+ * const dereferenced = await dereferenceArazzoElement(parseResult, {
166
+ * dereference: { strategyOpts: { sourceDescriptions: true } },
167
+ * });
168
+ * ```
169
+ * @public
170
+ */
171
+ async function dereferenceElement(element, options = {}) {
172
+ const mergedOptions = (0, _empty.mergeOptions)(defaultOptions, options);
173
+ const refSet = mergedOptions.dereference?.refSet ?? new _empty.ReferenceSet();
174
+ let baseURI = mergedOptions.resolve?.baseURI;
175
+ let mediaType = 'text/plain';
176
+ if (refSet.size === 0) {
177
+ if ((0, _apidomDatamodel.isParseResultElement)(element)) {
178
+ if ((0, _apidomNsArazzo.isArazzoSpecification1Element)(element.api)) {
179
+ mediaType = _apidomNsArazzo.mediaTypes.latest();
180
+ }
181
+ if (element.hasMetaProperty('retrievalURI')) {
182
+ baseURI = element.meta.get('retrievalURI');
183
+ } else if (!baseURI) {
184
+ throw new _DereferenceError.default('baseURI option is required when dereferencing a ParseResultElement without retrievalURI metadata');
185
+ }
186
+ } else if ((0, _apidomDatamodel.isParseResultElement)(mergedOptions.dereference?.strategyOpts?.parseResult)) {
187
+ // dereferencing child element requires refSet for component resolution
188
+ const {
189
+ parseResult
190
+ } = mergedOptions.dereference.strategyOpts;
191
+ let rootURI;
192
+ if ((0, _apidomNsArazzo.isArazzoSpecification1Element)(parseResult.api)) {
193
+ mediaType = _apidomNsArazzo.mediaTypes.latest();
194
+ }
195
+ if (parseResult.hasMetaProperty('retrievalURI')) {
196
+ rootURI = parseResult.meta.get('retrievalURI');
197
+ } else if (baseURI) {
198
+ rootURI = baseURI;
199
+ } else {
200
+ throw new _DereferenceError.default('baseURI option is required when dereferencing a child element without retrievalURI metadata');
201
+ }
202
+ const elementReference = new _empty.Reference({
203
+ uri: `${rootURI}#fragment`,
204
+ value: new _apidomDatamodel.ParseResultElement([element])
205
+ });
206
+ const rootReference = new _empty.Reference({
207
+ uri: rootURI,
208
+ value: parseResult
209
+ });
210
+ refSet.add(elementReference).add(rootReference);
211
+ baseURI = rootURI;
212
+ }
213
+ }
214
+ try {
215
+ return await (0, _empty.dereferenceApiDOM)(element, (0, _empty.mergeOptions)(mergedOptions, {
216
+ resolve: {
217
+ baseURI
218
+ },
219
+ parse: {
220
+ mediaType
221
+ },
222
+ dereference: {
223
+ refSet
224
+ }
225
+ }));
226
+ } catch (error) {
227
+ throw new _DereferenceError.default('Failed to dereference Arazzo Document', {
228
+ cause: error
229
+ });
230
+ }
231
+ }
@@ -0,0 +1,223 @@
1
+ import { isParseResultElement, ParseResultElement } from '@speclynx/apidom-datamodel';
2
+ import { dereference as dereferenceURI, dereferenceApiDOM as dereferenceApiDOMElement, mergeOptions, ReferenceSet, Reference, UnmatchedDereferenceStrategyError } from '@speclynx/apidom-reference/configuration/empty';
3
+ import Arazzo1DereferenceStrategy from '@speclynx/apidom-reference/dereference/strategies/arazzo-1';
4
+ import OpenAPI2DereferenceStrategy from '@speclynx/apidom-reference/dereference/strategies/openapi-2';
5
+ import OpenAPI30DereferenceStrategy from '@speclynx/apidom-reference/dereference/strategies/openapi-3-0';
6
+ import OpenAPI31DereferenceStrategy from '@speclynx/apidom-reference/dereference/strategies/openapi-3-1';
7
+ import JSONParser from '@speclynx/apidom-reference/parse/parsers/json';
8
+ import YAMLParser from '@speclynx/apidom-reference/parse/parsers/yaml-1-2';
9
+ import BinaryParser from '@speclynx/apidom-reference/parse/parsers/binary';
10
+ import { isArazzoSpecification1Element, mediaTypes } from '@speclynx/apidom-ns-arazzo-1';
11
+ import { defaultArazzoOptions as parserDefaultOptions } from '@jentic/arazzo-parser';
12
+ import DereferenceError from "../errors/DereferenceError.mjs";
13
+ /**
14
+ * Options for dereferencing Arazzo Documents.
15
+ * @public
16
+ */
17
+ /**
18
+ * Default reference options for dereferencing Arazzo Documents.
19
+ * @public
20
+ */
21
+ export const defaultOptions = {
22
+ resolve: {
23
+ resolvers: [...parserDefaultOptions.resolve.resolvers]
24
+ },
25
+ parse: {
26
+ parsers: [...parserDefaultOptions.parse.parsers, new JSONParser({
27
+ allowEmpty: false
28
+ }), new YAMLParser({
29
+ allowEmpty: false
30
+ }), new BinaryParser({
31
+ allowEmpty: false
32
+ })],
33
+ parserOpts: {
34
+ ...parserDefaultOptions.parse.parserOpts
35
+ }
36
+ },
37
+ dereference: {
38
+ strategies: [new Arazzo1DereferenceStrategy(), new OpenAPI2DereferenceStrategy(), new OpenAPI30DereferenceStrategy(), new OpenAPI31DereferenceStrategy()],
39
+ strategyOpts: {
40
+ sourceDescriptions: false
41
+ }
42
+ }
43
+ };
44
+
45
+ /**
46
+ * Dereferences an Arazzo Document from a file system path or HTTP(S) URL.
47
+ *
48
+ * This function resolves all JSON References ($ref) and Reusable Object references
49
+ * ($components.*) in the Arazzo Document.
50
+ *
51
+ * Source descriptions can optionally be dereferenced using strategy options:
52
+ * - `sourceDescriptions`: `true` (all) or `['name1', 'name2']` (specific names only)
53
+ * - `sourceDescriptionsMaxDepth`: Maximum recursion depth for nested Arazzo source descriptions (default: `+Infinity`)
54
+ *
55
+ * Options can be passed globally via `strategyOpts` or strategy-specific via `strategyOpts['arazzo-1']`.
56
+ *
57
+ * @param uri - A file system path or HTTP(S) URL to the Arazzo Document
58
+ * @param options - Reference options (uses defaultOptions when not provided)
59
+ * @returns A promise that resolves to the dereferenced Arazzo Document as ApiDOM element
60
+ * @throws DereferenceError - When dereferencing fails or document is not an Arazzo specification. The original error is available via the `cause` property.
61
+ *
62
+ * @example
63
+ * // Dereference from file
64
+ * const result = await dereferenceArazzo('/path/to/arazzo.json');
65
+ *
66
+ * @example
67
+ * // Dereference from URL
68
+ * const result = await dereferenceArazzo('https://example.com/arazzo.yaml');
69
+ *
70
+ * @example
71
+ * Dereference with source descriptions
72
+ * ```typescript
73
+ * const result = await dereferenceArazzo('/path/to/arazzo.json', {
74
+ * dereference: { strategyOpts: { sourceDescriptions: true } },
75
+ * });
76
+ * ```
77
+ *
78
+ * @example
79
+ * // Dereference with custom options
80
+ * const result = await dereferenceArazzo('/path/to/arazzo.json', customReferenceOptions);
81
+ * @public
82
+ */
83
+ export async function dereference(uri, options = {}) {
84
+ const mergedOptions = mergeOptions(defaultOptions, options);
85
+ try {
86
+ const parseResult = await dereferenceURI(uri, mergedOptions);
87
+
88
+ // validate that the dereferenced document is an Arazzo specification
89
+ if (!isArazzoSpecification1Element(parseResult.api)) {
90
+ throw new UnmatchedDereferenceStrategyError(`Could not find a dereference strategy that can dereference "${uri}" as an Arazzo specification`);
91
+ }
92
+ parseResult.meta.set('retrievalURI', uri);
93
+ return parseResult;
94
+ } catch (error) {
95
+ throw new DereferenceError(`Failed to dereference Arazzo Document at "${uri}"`, {
96
+ cause: error
97
+ });
98
+ }
99
+ }
100
+
101
+ /**
102
+ * Dereferences an ApiDOM element representing an Arazzo Document.
103
+ *
104
+ * This function resolves all JSON References ($ref) and Reusable Object references
105
+ * ($components.*) in the Arazzo Document element.
106
+ *
107
+ * Supported scenarios:
108
+ * - ParseResultElement with retrievalURI metadata: baseURI derived automatically
109
+ * - ParseResultElement without retrievalURI: requires `options.resolve.baseURI`
110
+ * - Child element (e.g., WorkflowElement) with parseResult in strategyOpts:
111
+ * requires `options.dereference.strategyOpts.parseResult` for component resolution,
112
+ * and `options.resolve.baseURI` if parseResult lacks retrievalURI metadata
113
+ *
114
+ * Source descriptions can optionally be dereferenced using strategy options:
115
+ * - `sourceDescriptions`: `true` (all) or `['name1', 'name2']` (specific names only)
116
+ * - `sourceDescriptionsMaxDepth`: Maximum recursion depth for nested Arazzo source descriptions (default: `+Infinity`)
117
+ *
118
+ * Options can be passed globally via `strategyOpts` or strategy-specific via `strategyOpts['arazzo-1']`.
119
+ *
120
+ * @param element - An ApiDOM element (ParseResultElement or child element like WorkflowElement)
121
+ * @param options - Reference options (uses defaultOptions when not provided)
122
+ * @returns A promise that resolves to the dereferenced element
123
+ * @throws DereferenceError - When baseURI is required but not provided, or when dereferencing fails
124
+ *
125
+ * @example
126
+ * Dereference ParseResultElement with retrievalURI (from file parsing)
127
+ * ```typescript
128
+ * import { parseArazzo } from '@jentic/arazzo-parser';
129
+ *
130
+ * const parseResult = await parseArazzo('/path/to/arazzo.json');
131
+ * const dereferenced = await dereferenceArazzoElement(parseResult);
132
+ * ```
133
+ *
134
+ * @example
135
+ * Dereference ParseResultElement without retrievalURI (from inline parsing)
136
+ * ```typescript
137
+ * const parseResult = await parseArazzo({ arazzo: '1.0.1', ... });
138
+ * const dereferenced = await dereferenceArazzoElement(parseResult, {
139
+ * resolve: { baseURI: 'https://example.com/arazzo.json' },
140
+ * });
141
+ * ```
142
+ *
143
+ * @example
144
+ * Dereference child element (e.g., WorkflowElement)
145
+ * ```typescript
146
+ * const parseResult = await parseArazzo('/path/to/arazzo.json');
147
+ * const workflow = parseResult.api.workflows.get(0);
148
+ * const dereferenced = await dereferenceArazzoElement(workflow, {
149
+ * dereference: { strategyOpts: { parseResult } },
150
+ * });
151
+ * ```
152
+ *
153
+ * @example
154
+ * Dereference with source descriptions
155
+ * ```typescript
156
+ * const parseResult = await parseArazzo('/path/to/arazzo.json');
157
+ * const dereferenced = await dereferenceArazzoElement(parseResult, {
158
+ * dereference: { strategyOpts: { sourceDescriptions: true } },
159
+ * });
160
+ * ```
161
+ * @public
162
+ */
163
+ export async function dereferenceElement(element, options = {}) {
164
+ const mergedOptions = mergeOptions(defaultOptions, options);
165
+ const refSet = mergedOptions.dereference?.refSet ?? new ReferenceSet();
166
+ let baseURI = mergedOptions.resolve?.baseURI;
167
+ let mediaType = 'text/plain';
168
+ if (refSet.size === 0) {
169
+ if (isParseResultElement(element)) {
170
+ if (isArazzoSpecification1Element(element.api)) {
171
+ mediaType = mediaTypes.latest();
172
+ }
173
+ if (element.hasMetaProperty('retrievalURI')) {
174
+ baseURI = element.meta.get('retrievalURI');
175
+ } else if (!baseURI) {
176
+ throw new DereferenceError('baseURI option is required when dereferencing a ParseResultElement without retrievalURI metadata');
177
+ }
178
+ } else if (isParseResultElement(mergedOptions.dereference?.strategyOpts?.parseResult)) {
179
+ // dereferencing child element requires refSet for component resolution
180
+ const {
181
+ parseResult
182
+ } = mergedOptions.dereference.strategyOpts;
183
+ let rootURI;
184
+ if (isArazzoSpecification1Element(parseResult.api)) {
185
+ mediaType = mediaTypes.latest();
186
+ }
187
+ if (parseResult.hasMetaProperty('retrievalURI')) {
188
+ rootURI = parseResult.meta.get('retrievalURI');
189
+ } else if (baseURI) {
190
+ rootURI = baseURI;
191
+ } else {
192
+ throw new DereferenceError('baseURI option is required when dereferencing a child element without retrievalURI metadata');
193
+ }
194
+ const elementReference = new Reference({
195
+ uri: `${rootURI}#fragment`,
196
+ value: new ParseResultElement([element])
197
+ });
198
+ const rootReference = new Reference({
199
+ uri: rootURI,
200
+ value: parseResult
201
+ });
202
+ refSet.add(elementReference).add(rootReference);
203
+ baseURI = rootURI;
204
+ }
205
+ }
206
+ try {
207
+ return await dereferenceApiDOMElement(element, mergeOptions(mergedOptions, {
208
+ resolve: {
209
+ baseURI
210
+ },
211
+ parse: {
212
+ mediaType
213
+ },
214
+ dereference: {
215
+ refSet
216
+ }
217
+ }));
218
+ } catch (error) {
219
+ throw new DereferenceError('Failed to dereference Arazzo Document', {
220
+ cause: error
221
+ });
222
+ }
223
+ }
@@ -0,0 +1,224 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime-corejs3/helpers/interopRequireDefault").default;
4
+ exports.__esModule = true;
5
+ exports.defaultOptions = void 0;
6
+ exports.dereference = dereference;
7
+ exports.dereferenceElement = dereferenceElement;
8
+ var _apidomDatamodel = require("@speclynx/apidom-datamodel");
9
+ var _empty = require("@speclynx/apidom-reference/configuration/empty");
10
+ var _openapi = _interopRequireDefault(require("@speclynx/apidom-reference/dereference/strategies/openapi-2"));
11
+ var _openapi2 = _interopRequireDefault(require("@speclynx/apidom-reference/dereference/strategies/openapi-3-0"));
12
+ var _openapi3 = _interopRequireDefault(require("@speclynx/apidom-reference/dereference/strategies/openapi-3-1"));
13
+ var _json = _interopRequireDefault(require("@speclynx/apidom-reference/parse/parsers/json"));
14
+ var _yaml = _interopRequireDefault(require("@speclynx/apidom-reference/parse/parsers/yaml-1-2"));
15
+ var _binary = _interopRequireDefault(require("@speclynx/apidom-reference/parse/parsers/binary"));
16
+ var _apidomNsOpenapi = require("@speclynx/apidom-ns-openapi-2");
17
+ var _apidomNsOpenapi2 = require("@speclynx/apidom-ns-openapi-3-0");
18
+ var _apidomNsOpenapi3 = require("@speclynx/apidom-ns-openapi-3-1");
19
+ var _arazzoParser = require("@jentic/arazzo-parser");
20
+ var _DereferenceError = _interopRequireDefault(require("../errors/DereferenceError.cjs"));
21
+ /**
22
+ * Options for dereferencing OpenAPI Documents.
23
+ * @public
24
+ */
25
+
26
+ /**
27
+ * Default reference options for dereferencing OpenAPI Documents.
28
+ * @public
29
+ */
30
+ const defaultOptions = exports.defaultOptions = {
31
+ resolve: {
32
+ resolvers: [..._arazzoParser.defaultOpenAPIOptions.resolve.resolvers]
33
+ },
34
+ parse: {
35
+ parsers: [..._arazzoParser.defaultOpenAPIOptions.parse.parsers, new _json.default({
36
+ allowEmpty: false
37
+ }), new _yaml.default({
38
+ allowEmpty: false
39
+ }), new _binary.default({
40
+ allowEmpty: false
41
+ })],
42
+ parserOpts: {
43
+ ..._arazzoParser.defaultOpenAPIOptions.parse.parserOpts
44
+ }
45
+ },
46
+ dereference: {
47
+ strategies: [new _openapi.default(), new _openapi2.default(), new _openapi3.default()],
48
+ strategyOpts: {}
49
+ }
50
+ };
51
+
52
+ /**
53
+ * Dereferences an OpenAPI Document from a file system path or HTTP(S) URL.
54
+ *
55
+ * This function resolves all JSON References ($ref) in the OpenAPI Document.
56
+ *
57
+ * Supports OpenAPI 2.0 (Swagger), OpenAPI 3.0.x, and OpenAPI 3.1.x.
58
+ *
59
+ * @param uri - A file system path or HTTP(S) URL to the OpenAPI Document
60
+ * @param options - Reference options (uses defaultOptions when not provided)
61
+ * @returns A promise that resolves to the dereferenced OpenAPI Document as ApiDOM element
62
+ * @throws DereferenceError - When dereferencing fails or document is not an OpenAPI specification. The original error is available via the `cause` property.
63
+ *
64
+ * @example
65
+ * // Dereference from file
66
+ * const result = await dereferenceOpenAPI('/path/to/openapi.json');
67
+ *
68
+ * @example
69
+ * // Dereference from URL
70
+ * const result = await dereferenceOpenAPI('https://example.com/openapi.yaml');
71
+ *
72
+ * @example
73
+ * // Dereference with custom options
74
+ * const result = await dereferenceOpenAPI('/path/to/openapi.json', customReferenceOptions);
75
+ * @public
76
+ */
77
+ async function dereference(uri, options = {}) {
78
+ const mergedOptions = (0, _empty.mergeOptions)(defaultOptions, options);
79
+ try {
80
+ const parseResult = await (0, _empty.dereference)(uri, mergedOptions);
81
+
82
+ // validate that the dereferenced document is an OpenAPI specification
83
+ if (!isOpenApiElement(parseResult.api)) {
84
+ throw new _empty.UnmatchedDereferenceStrategyError(`Could not find a dereference strategy that can dereference "${uri}" as an OpenAPI specification`);
85
+ }
86
+ parseResult.meta.set('retrievalURI', uri);
87
+ return parseResult;
88
+ } catch (error) {
89
+ throw new _DereferenceError.default(`Failed to dereference OpenAPI Document at "${uri}"`, {
90
+ cause: error
91
+ });
92
+ }
93
+ }
94
+
95
+ /**
96
+ * Dereferences an ApiDOM element representing an OpenAPI Document.
97
+ *
98
+ * This function resolves all JSON References ($ref) in the OpenAPI Document element.
99
+ *
100
+ * Supported scenarios:
101
+ * - ParseResultElement with retrievalURI metadata: baseURI derived automatically
102
+ * - ParseResultElement without retrievalURI: requires `options.resolve.baseURI`
103
+ * - Child element (e.g., PathItemElement) with parseResult in strategyOpts:
104
+ * requires `options.dereference.strategyOpts.parseResult` for component resolution,
105
+ * and `options.resolve.baseURI` if parseResult lacks retrievalURI metadata
106
+ *
107
+ * @param element - An ApiDOM element (ParseResultElement or child element like PathItemElement)
108
+ * @param options - Reference options (uses defaultOptions when not provided)
109
+ * @returns A promise that resolves to the dereferenced element
110
+ * @throws DereferenceError - When baseURI is required but not provided, or when dereferencing fails
111
+ *
112
+ * @example
113
+ * Dereference ParseResultElement with retrievalURI (from file parsing)
114
+ * ```typescript
115
+ * import { parseOpenAPI } from '@jentic/arazzo-parser';
116
+ *
117
+ * const parseResult = await parseOpenAPI('/path/to/openapi.json');
118
+ * const dereferenced = await dereferenceOpenAPIElement(parseResult);
119
+ * ```
120
+ *
121
+ * @example
122
+ * Dereference ParseResultElement without retrievalURI (from inline parsing)
123
+ * ```typescript
124
+ * const parseResult = await parseOpenAPI({ openapi: '3.1.0', ... });
125
+ * const dereferenced = await dereferenceOpenAPIElement(parseResult, {
126
+ * resolve: { baseURI: 'https://example.com/openapi.json' },
127
+ * });
128
+ * ```
129
+ *
130
+ * @example
131
+ * Dereference child element (e.g., PathItemElement)
132
+ * ```typescript
133
+ * const parseResult = await parseOpenAPI('/path/to/openapi.json');
134
+ * const pathItem = parseResult.api.paths.get('/users');
135
+ * const dereferenced = await dereferenceOpenAPIElement(pathItem, {
136
+ * dereference: { strategyOpts: { parseResult } },
137
+ * });
138
+ * ```
139
+ * @public
140
+ */
141
+ async function dereferenceElement(element, options = {}) {
142
+ const mergedOptions = (0, _empty.mergeOptions)(defaultOptions, options);
143
+ const refSet = mergedOptions.dereference?.refSet ?? new _empty.ReferenceSet();
144
+ let baseURI = mergedOptions.resolve?.baseURI;
145
+ let mediaType = 'text/plain';
146
+ if (refSet.size === 0) {
147
+ if ((0, _apidomDatamodel.isParseResultElement)(element)) {
148
+ if (isOpenApiElement(element.api)) {
149
+ mediaType = inferOpenApiMediaType(element.api);
150
+ }
151
+ if (element.hasMetaProperty('retrievalURI')) {
152
+ baseURI = element.meta.get('retrievalURI');
153
+ } else if (!baseURI) {
154
+ throw new _DereferenceError.default('baseURI option is required when dereferencing a ParseResultElement without retrievalURI metadata');
155
+ }
156
+ } else if ((0, _apidomDatamodel.isParseResultElement)(mergedOptions.dereference?.strategyOpts?.parseResult)) {
157
+ // dereferencing child element requires refSet for component resolution
158
+ const {
159
+ parseResult
160
+ } = mergedOptions.dereference.strategyOpts;
161
+ let rootURI;
162
+ if (isOpenApiElement(parseResult.api)) {
163
+ mediaType = inferOpenApiMediaType(parseResult.api);
164
+ }
165
+ if (parseResult.hasMetaProperty('retrievalURI')) {
166
+ rootURI = parseResult.meta.get('retrievalURI');
167
+ } else if (baseURI) {
168
+ rootURI = baseURI;
169
+ } else {
170
+ throw new _DereferenceError.default('baseURI option is required when dereferencing a child element without retrievalURI metadata');
171
+ }
172
+ const elementReference = new _empty.Reference({
173
+ uri: `${rootURI}#fragment`,
174
+ value: new _apidomDatamodel.ParseResultElement([element])
175
+ });
176
+ const rootReference = new _empty.Reference({
177
+ uri: rootURI,
178
+ value: parseResult
179
+ });
180
+ refSet.add(elementReference).add(rootReference);
181
+ baseURI = rootURI;
182
+ }
183
+ }
184
+ try {
185
+ return await (0, _empty.dereferenceApiDOM)(element, (0, _empty.mergeOptions)(mergedOptions, {
186
+ resolve: {
187
+ baseURI
188
+ },
189
+ parse: {
190
+ mediaType
191
+ },
192
+ dereference: {
193
+ refSet
194
+ }
195
+ }));
196
+ } catch (error) {
197
+ throw new _DereferenceError.default('Failed to dereference OpenAPI Document', {
198
+ cause: error
199
+ });
200
+ }
201
+ }
202
+
203
+ /**
204
+ * Checks if the element is a valid OpenAPI specification element.
205
+ */
206
+ function isOpenApiElement(element) {
207
+ return (0, _apidomNsOpenapi.isSwaggerElement)(element) || (0, _apidomNsOpenapi2.isOpenApi3_0Element)(element) || (0, _apidomNsOpenapi3.isOpenApi3_1Element)(element);
208
+ }
209
+
210
+ /**
211
+ * Gets the appropriate mediaType for an OpenAPI element.
212
+ */
213
+ function inferOpenApiMediaType(element) {
214
+ if ((0, _apidomNsOpenapi.isSwaggerElement)(element)) {
215
+ return _apidomNsOpenapi.mediaTypes.latest();
216
+ }
217
+ if ((0, _apidomNsOpenapi2.isOpenApi3_0Element)(element)) {
218
+ return _apidomNsOpenapi2.mediaTypes.latest();
219
+ }
220
+ if ((0, _apidomNsOpenapi3.isOpenApi3_1Element)(element)) {
221
+ return _apidomNsOpenapi3.mediaTypes.latest();
222
+ }
223
+ return 'text/plain';
224
+ }
@@ -0,0 +1,216 @@
1
+ import { isParseResultElement, ParseResultElement } from '@speclynx/apidom-datamodel';
2
+ import { dereference as dereferenceURI, dereferenceApiDOM as dereferenceApiDOMElement, mergeOptions, ReferenceSet, Reference, UnmatchedDereferenceStrategyError } from '@speclynx/apidom-reference/configuration/empty';
3
+ import OpenAPI2DereferenceStrategy from '@speclynx/apidom-reference/dereference/strategies/openapi-2';
4
+ import OpenAPI3_0DereferenceStrategy from '@speclynx/apidom-reference/dereference/strategies/openapi-3-0';
5
+ import OpenAPI3_1DereferenceStrategy from '@speclynx/apidom-reference/dereference/strategies/openapi-3-1';
6
+ import JSONParser from '@speclynx/apidom-reference/parse/parsers/json';
7
+ import YAMLParser from '@speclynx/apidom-reference/parse/parsers/yaml-1-2';
8
+ import BinaryParser from '@speclynx/apidom-reference/parse/parsers/binary';
9
+ import { isSwaggerElement, mediaTypes as openApi2MediaTypes } from '@speclynx/apidom-ns-openapi-2';
10
+ import { isOpenApi3_0Element, mediaTypes as openApi3_0MediaTypes } from '@speclynx/apidom-ns-openapi-3-0';
11
+ import { isOpenApi3_1Element, mediaTypes as openApi3_1MediaTypes } from '@speclynx/apidom-ns-openapi-3-1';
12
+ import { defaultOpenAPIOptions as parserDefaultOptions } from '@jentic/arazzo-parser';
13
+ import DereferenceError from "../errors/DereferenceError.mjs";
14
+ /**
15
+ * Options for dereferencing OpenAPI Documents.
16
+ * @public
17
+ */
18
+ /**
19
+ * Default reference options for dereferencing OpenAPI Documents.
20
+ * @public
21
+ */
22
+ export const defaultOptions = {
23
+ resolve: {
24
+ resolvers: [...parserDefaultOptions.resolve.resolvers]
25
+ },
26
+ parse: {
27
+ parsers: [...parserDefaultOptions.parse.parsers, new JSONParser({
28
+ allowEmpty: false
29
+ }), new YAMLParser({
30
+ allowEmpty: false
31
+ }), new BinaryParser({
32
+ allowEmpty: false
33
+ })],
34
+ parserOpts: {
35
+ ...parserDefaultOptions.parse.parserOpts
36
+ }
37
+ },
38
+ dereference: {
39
+ strategies: [new OpenAPI2DereferenceStrategy(), new OpenAPI3_0DereferenceStrategy(), new OpenAPI3_1DereferenceStrategy()],
40
+ strategyOpts: {}
41
+ }
42
+ };
43
+
44
+ /**
45
+ * Dereferences an OpenAPI Document from a file system path or HTTP(S) URL.
46
+ *
47
+ * This function resolves all JSON References ($ref) in the OpenAPI Document.
48
+ *
49
+ * Supports OpenAPI 2.0 (Swagger), OpenAPI 3.0.x, and OpenAPI 3.1.x.
50
+ *
51
+ * @param uri - A file system path or HTTP(S) URL to the OpenAPI Document
52
+ * @param options - Reference options (uses defaultOptions when not provided)
53
+ * @returns A promise that resolves to the dereferenced OpenAPI Document as ApiDOM element
54
+ * @throws DereferenceError - When dereferencing fails or document is not an OpenAPI specification. The original error is available via the `cause` property.
55
+ *
56
+ * @example
57
+ * // Dereference from file
58
+ * const result = await dereferenceOpenAPI('/path/to/openapi.json');
59
+ *
60
+ * @example
61
+ * // Dereference from URL
62
+ * const result = await dereferenceOpenAPI('https://example.com/openapi.yaml');
63
+ *
64
+ * @example
65
+ * // Dereference with custom options
66
+ * const result = await dereferenceOpenAPI('/path/to/openapi.json', customReferenceOptions);
67
+ * @public
68
+ */
69
+ export async function dereference(uri, options = {}) {
70
+ const mergedOptions = mergeOptions(defaultOptions, options);
71
+ try {
72
+ const parseResult = await dereferenceURI(uri, mergedOptions);
73
+
74
+ // validate that the dereferenced document is an OpenAPI specification
75
+ if (!isOpenApiElement(parseResult.api)) {
76
+ throw new UnmatchedDereferenceStrategyError(`Could not find a dereference strategy that can dereference "${uri}" as an OpenAPI specification`);
77
+ }
78
+ parseResult.meta.set('retrievalURI', uri);
79
+ return parseResult;
80
+ } catch (error) {
81
+ throw new DereferenceError(`Failed to dereference OpenAPI Document at "${uri}"`, {
82
+ cause: error
83
+ });
84
+ }
85
+ }
86
+
87
+ /**
88
+ * Dereferences an ApiDOM element representing an OpenAPI Document.
89
+ *
90
+ * This function resolves all JSON References ($ref) in the OpenAPI Document element.
91
+ *
92
+ * Supported scenarios:
93
+ * - ParseResultElement with retrievalURI metadata: baseURI derived automatically
94
+ * - ParseResultElement without retrievalURI: requires `options.resolve.baseURI`
95
+ * - Child element (e.g., PathItemElement) with parseResult in strategyOpts:
96
+ * requires `options.dereference.strategyOpts.parseResult` for component resolution,
97
+ * and `options.resolve.baseURI` if parseResult lacks retrievalURI metadata
98
+ *
99
+ * @param element - An ApiDOM element (ParseResultElement or child element like PathItemElement)
100
+ * @param options - Reference options (uses defaultOptions when not provided)
101
+ * @returns A promise that resolves to the dereferenced element
102
+ * @throws DereferenceError - When baseURI is required but not provided, or when dereferencing fails
103
+ *
104
+ * @example
105
+ * Dereference ParseResultElement with retrievalURI (from file parsing)
106
+ * ```typescript
107
+ * import { parseOpenAPI } from '@jentic/arazzo-parser';
108
+ *
109
+ * const parseResult = await parseOpenAPI('/path/to/openapi.json');
110
+ * const dereferenced = await dereferenceOpenAPIElement(parseResult);
111
+ * ```
112
+ *
113
+ * @example
114
+ * Dereference ParseResultElement without retrievalURI (from inline parsing)
115
+ * ```typescript
116
+ * const parseResult = await parseOpenAPI({ openapi: '3.1.0', ... });
117
+ * const dereferenced = await dereferenceOpenAPIElement(parseResult, {
118
+ * resolve: { baseURI: 'https://example.com/openapi.json' },
119
+ * });
120
+ * ```
121
+ *
122
+ * @example
123
+ * Dereference child element (e.g., PathItemElement)
124
+ * ```typescript
125
+ * const parseResult = await parseOpenAPI('/path/to/openapi.json');
126
+ * const pathItem = parseResult.api.paths.get('/users');
127
+ * const dereferenced = await dereferenceOpenAPIElement(pathItem, {
128
+ * dereference: { strategyOpts: { parseResult } },
129
+ * });
130
+ * ```
131
+ * @public
132
+ */
133
+ export async function dereferenceElement(element, options = {}) {
134
+ const mergedOptions = mergeOptions(defaultOptions, options);
135
+ const refSet = mergedOptions.dereference?.refSet ?? new ReferenceSet();
136
+ let baseURI = mergedOptions.resolve?.baseURI;
137
+ let mediaType = 'text/plain';
138
+ if (refSet.size === 0) {
139
+ if (isParseResultElement(element)) {
140
+ if (isOpenApiElement(element.api)) {
141
+ mediaType = inferOpenApiMediaType(element.api);
142
+ }
143
+ if (element.hasMetaProperty('retrievalURI')) {
144
+ baseURI = element.meta.get('retrievalURI');
145
+ } else if (!baseURI) {
146
+ throw new DereferenceError('baseURI option is required when dereferencing a ParseResultElement without retrievalURI metadata');
147
+ }
148
+ } else if (isParseResultElement(mergedOptions.dereference?.strategyOpts?.parseResult)) {
149
+ // dereferencing child element requires refSet for component resolution
150
+ const {
151
+ parseResult
152
+ } = mergedOptions.dereference.strategyOpts;
153
+ let rootURI;
154
+ if (isOpenApiElement(parseResult.api)) {
155
+ mediaType = inferOpenApiMediaType(parseResult.api);
156
+ }
157
+ if (parseResult.hasMetaProperty('retrievalURI')) {
158
+ rootURI = parseResult.meta.get('retrievalURI');
159
+ } else if (baseURI) {
160
+ rootURI = baseURI;
161
+ } else {
162
+ throw new DereferenceError('baseURI option is required when dereferencing a child element without retrievalURI metadata');
163
+ }
164
+ const elementReference = new Reference({
165
+ uri: `${rootURI}#fragment`,
166
+ value: new ParseResultElement([element])
167
+ });
168
+ const rootReference = new Reference({
169
+ uri: rootURI,
170
+ value: parseResult
171
+ });
172
+ refSet.add(elementReference).add(rootReference);
173
+ baseURI = rootURI;
174
+ }
175
+ }
176
+ try {
177
+ return await dereferenceApiDOMElement(element, mergeOptions(mergedOptions, {
178
+ resolve: {
179
+ baseURI
180
+ },
181
+ parse: {
182
+ mediaType
183
+ },
184
+ dereference: {
185
+ refSet
186
+ }
187
+ }));
188
+ } catch (error) {
189
+ throw new DereferenceError('Failed to dereference OpenAPI Document', {
190
+ cause: error
191
+ });
192
+ }
193
+ }
194
+
195
+ /**
196
+ * Checks if the element is a valid OpenAPI specification element.
197
+ */
198
+ function isOpenApiElement(element) {
199
+ return isSwaggerElement(element) || isOpenApi3_0Element(element) || isOpenApi3_1Element(element);
200
+ }
201
+
202
+ /**
203
+ * Gets the appropriate mediaType for an OpenAPI element.
204
+ */
205
+ function inferOpenApiMediaType(element) {
206
+ if (isSwaggerElement(element)) {
207
+ return openApi2MediaTypes.latest();
208
+ }
209
+ if (isOpenApi3_0Element(element)) {
210
+ return openApi3_0MediaTypes.latest();
211
+ }
212
+ if (isOpenApi3_1Element(element)) {
213
+ return openApi3_1MediaTypes.latest();
214
+ }
215
+ return 'text/plain';
216
+ }
@@ -0,0 +1,15 @@
1
+ "use strict";
2
+
3
+ exports.__esModule = true;
4
+ exports.default = void 0;
5
+ var _apidomError = require("@speclynx/apidom-error");
6
+ /**
7
+ * Error thrown when dereferencing an Arazzo document or element fails.
8
+ * @public
9
+ */
10
+ class DereferenceError extends _apidomError.ApiDOMError {
11
+ constructor(message, options) {
12
+ super(message, options);
13
+ }
14
+ }
15
+ var _default = exports.default = DereferenceError;
@@ -0,0 +1,12 @@
1
+ import { ApiDOMError } from '@speclynx/apidom-error';
2
+
3
+ /**
4
+ * Error thrown when dereferencing an Arazzo document or element fails.
5
+ * @public
6
+ */
7
+ class DereferenceError extends ApiDOMError {
8
+ constructor(message, options) {
9
+ super(message, options);
10
+ }
11
+ }
12
+ export default DereferenceError;
package/src/index.cjs ADDED
@@ -0,0 +1,15 @@
1
+ "use strict";
2
+
3
+ var _interopRequireDefault = require("@babel/runtime-corejs3/helpers/interopRequireDefault").default;
4
+ exports.__esModule = true;
5
+ exports.dereferenceOpenAPIElement = exports.dereferenceOpenAPI = exports.dereferenceArazzoElement = exports.dereferenceArazzo = exports.defaultDereferenceOpenAPIOptions = exports.defaultDereferenceArazzoOptions = exports.DereferenceError = void 0;
6
+ var _arazzo = require("./dereference/arazzo.cjs");
7
+ exports.defaultDereferenceArazzoOptions = _arazzo.defaultOptions;
8
+ exports.dereferenceArazzo = _arazzo.dereference;
9
+ exports.dereferenceArazzoElement = _arazzo.dereferenceElement;
10
+ var _openapi = require("./dereference/openapi.cjs");
11
+ exports.defaultDereferenceOpenAPIOptions = _openapi.defaultOptions;
12
+ exports.dereferenceOpenAPI = _openapi.dereference;
13
+ exports.dereferenceOpenAPIElement = _openapi.dereferenceElement;
14
+ var _DereferenceError = _interopRequireDefault(require("./errors/DereferenceError.cjs"));
15
+ exports.DereferenceError = _DereferenceError.default;
package/src/index.mjs ADDED
@@ -0,0 +1,3 @@
1
+ export { defaultOptions as defaultDereferenceArazzoOptions, dereference as dereferenceArazzo, dereferenceElement as dereferenceArazzoElement } from "./dereference/arazzo.mjs";
2
+ export { defaultOptions as defaultDereferenceOpenAPIOptions, dereference as dereferenceOpenAPI, dereferenceElement as dereferenceOpenAPIElement } from "./dereference/openapi.mjs";
3
+ export { default as DereferenceError } from "./errors/DereferenceError.mjs";