{"id":35214544,"url":"https://github.com/speclynx/apidom","last_synced_at":"2026-04-21T18:01:03.383Z","repository":{"id":330034524,"uuid":"1121339641","full_name":"speclynx/apidom","owner":"speclynx","description":"Semantic parser for API specifications","archived":false,"fork":false,"pushed_at":"2026-04-17T15:25:50.000Z","size":13054,"stargazers_count":2,"open_issues_count":8,"forks_count":1,"subscribers_count":1,"default_branch":"main","last_synced_at":"2026-04-17T17:27:45.980Z","etag":null,"topics":["api","arazzo","asyncapi","asyncapi2","javascript","openapi","openapi2","openapi3","openapi31","parser","typescript"],"latest_commit_sha":null,"homepage":"https://speclynx.com/apidom/","language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"apache-2.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/speclynx.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":"CONTRIBUTING.md","funding":null,"license":"LICENSE","code_of_conduct":"CODE_OF_CONDUCT.md","threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":".github/SECURITY.md","support":".github/SUPPORT.md","governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null,"notice":"NOTICE","maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2025-12-22T20:38:38.000Z","updated_at":"2026-04-17T15:25:54.000Z","dependencies_parsed_at":null,"dependency_job_id":null,"html_url":"https://github.com/speclynx/apidom","commit_stats":null,"previous_names":["speclynx/apidom"],"tags_count":51,"template":false,"template_full_name":null,"purl":"pkg:github/speclynx/apidom","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/speclynx%2Fapidom","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/speclynx%2Fapidom/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/speclynx%2Fapidom/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/speclynx%2Fapidom/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/speclynx","download_url":"https://codeload.github.com/speclynx/apidom/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/speclynx%2Fapidom/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":32099196,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-21T11:25:29.218Z","status":"ssl_error","status_checked_at":"2026-04-21T11:25:28.499Z","response_time":128,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.5:443 state=error: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["api","arazzo","asyncapi","asyncapi2","javascript","openapi","openapi2","openapi3","openapi31","parser","typescript"],"created_at":"2025-12-29T21:20:40.563Z","updated_at":"2026-04-21T18:01:03.376Z","avatar_url":"https://github.com/speclynx.png","language":"TypeScript","readme":"[comment]: \u003c\u003e (SPDX-FileCopyrightText: Copyright \u0026#40;c\u0026#41; 2015 refractproject)\n[comment]: \u003c\u003e (SPDX-License-Identifier: MIT)\n\n[comment]: \u003c\u003e (SPDX-FileCopyrightText: Copyright \u0026#40;c\u0026#41; 2015 Apiary Inc.)\n[comment]: \u003c\u003e (SPDX-License-Identifier: MIT)\n\n# SpecLynx ApiDOM\n\n[![Build Status](https://github.com/speclynx/apidom/actions/workflows/build.yml/badge.svg)](https://github.com/speclynx/apidom/actions)\n[![Dependabot enabled](https://badgen.net/badge/icon/dependabot?icon=dependabot\u0026label)](https://docs.github.com/en/code-security/supply-chain-security/keeping-your-dependencies-updated-automatically)\n[![Contributor Covenant](https://img.shields.io/badge/Contributor%20Covenant-3.0-40c463.svg)](https://github.com/speclynx/apidom/blob/HEAD/CODE_OF_CONDUCT.md)\n[![License: Apache 2.0](https://img.shields.io/badge/License-Apache%202.0-blue.svg)](https://github.com/speclynx/apidom/blob/HEAD/LICENSES)\n\n\u003cdiv align=\"center\"\u003e\n    \u003ca href=\"https://speclynx.com\"\u003e\u003cimg width=\"636\" height=\"407\" alt=\"image\" src=\"https://github.com/user-attachments/assets/1cfd6c8e-0206-4d53-9a2c-e4d10be84ca0\" /\u003e\u003c/a\u003e\n\u003c/div\u003e\n\nThe purpose of ApiDOM is to provide a single, unifying structure for describing APIs across\nAPI description language and serialization formats. There currently exists several API description languages one can choose\nwhen defining an API, from OpenAPI, RAML, API Blueprint or others.\nThere are also many serialization formats such as XML, YAML or JSON. Without a way to parse these formats\nto the same structure, developers are required to handle each format one-by-one, each in a different\nway and each translating to their internal domain model. This is tedious, time-consuming,\nand requires each maintainer to stay in step with every format they support.\n\nApiDOM solves this complex problem in a simple way. It allows parsers to parse to a single structure\nand allows tool builders to consume one structure for all formats.\n\n## Table of Contents\n\n- [Getting started](#getting-started)\n  - [Installation](#installation)\n  - [Usage](#usage)\n  - [ApiDOM Playground](#apidom-playground)\n- [Development](#development)\n  - [Setting up](#setting-up)\n  - [Setting up via docker](#setting-up-via-docker)\n  - [Setting up via GitHub Codespaces](#setting-up-via-github-codespaces)\n  - [npm scripts](#npm-scripts)\n  - [Build artifacts](#build-artifacts)\n  - [Using this monorepo as a local dev dependency](#using-this-monorepo-as-a-local-dev-dependency)\n- [Documentation](#documentation)\n  - [What is an Element ?](#what-is-an-element-)\n  - [As a way to annotate JSON](#as-a-way-to-annotate-json)\n  - [As a unifying structure](#as-a-unifying-structure)\n  - [As a queryable structure](#as-a-queryable-structure)\n  - [ApiDOM stages](#apidom-stages)\n- [License](#license)\n- [Software Bill Of Materials (SBOM)](#software-bill-of-materials-sbom)\n\n## Getting started\n\n### Installation\n\nApiDOM npm packages are installable and works with `Node.js \u003e=16.14.2 \u003c=24`.\n\nYou can install ApiDOM packages using [npm CLI](https://docs.npmjs.com/cli):\n\n```sh\n $ npm install @speclynx/apidom-converter\n $ npm install @speclynx/apidom-core\n $ npm install @speclynx/apidom-datamodel\n $ npm install @speclynx/apidom-error\n $ npm install @speclynx/apidom-json-path\n $ npm install @speclynx/apidom-json-pointer\n $ npm install @speclynx/apidom-json-pointer-relative\n $ npm install @speclynx/apidom-overlay\n $ npm install @speclynx/apidom-ns-arazzo-1\n $ npm install @speclynx/apidom-ns-asyncapi-2\n $ npm install @speclynx/apidom-ns-overlay-1\n $ npm install @speclynx/apidom-ns-json-schema-2019-09\n $ npm install @speclynx/apidom-ns-json-schema-2020-12\n $ npm install @speclynx/apidom-ns-json-schema-draft-4\n $ npm install @speclynx/apidom-ns-json-schema-draft-6\n $ npm install @speclynx/apidom-ns-json-schema-draft-7\n $ npm install @speclynx/apidom-ns-openapi-2\n $ npm install @speclynx/apidom-ns-openapi-3-0\n $ npm install @speclynx/apidom-ns-openapi-3-1\n $ npm install @speclynx/apidom-parser\n $ npm install @speclynx/apidom-parser-adapter-arazzo-json-1\n $ npm install @speclynx/apidom-parser-adapter-arazzo-yaml-1\n $ npm install @speclynx/apidom-parser-adapter-asyncapi-json-2\n $ npm install @speclynx/apidom-parser-adapter-asyncapi-yaml-2\n $ npm install @speclynx/apidom-parser-adapter-json\n $ npm install @speclynx/apidom-parser-adapter-json-schema-json-2020-12\n $ npm install @speclynx/apidom-parser-adapter-json-schema-yaml-2020-12\n $ npm install @speclynx/apidom-parser-adapter-openapi-json-2\n $ npm install @speclynx/apidom-parser-adapter-openapi-json-3-0\n $ npm install @speclynx/apidom-parser-adapter-openapi-json-3-1\n $ npm install @speclynx/apidom-parser-adapter-openapi-yaml-2\n $ npm install @speclynx/apidom-parser-adapter-openapi-yaml-3-0\n $ npm install @speclynx/apidom-parser-adapter-openapi-yaml-3-1\n $ npm install @speclynx/apidom-parser-adapter-overlay-json-1\n $ npm install @speclynx/apidom-parser-adapter-overlay-yaml-1\n $ npm install @speclynx/apidom-parser-adapter-yaml-1-2\n $ npm install @speclynx/apidom-reference\n $ npm install @speclynx/apidom-traverse\n```\n\n### Usage\n\nEvery package of the monorepo has an associated README file demonstrating its purpose and containing\nusage examples.\n\n### ApiDOM Playground\n\nApiDOM Playground is a React application that runs in a browser and can visually demonstrate capabilities\nof the ApiDOM. ApiDOM Playground is build and deployed whenever the new commit lands on `main` branch.\n\n![image](https://user-images.githubusercontent.com/193286/145010522-5d85e34b-8d28-4a07-9ee2-b28807a013cd.png)\n\nApiDOM Playground is available at [https://speclynx.github.io/apidom/](https://speclynx.github.io/apidom/)\n\n## Development\n\nThis is a monorepo for all ApiDOM packages. All the code is written in [TypeScript](https://www.typescriptlang.org/).\nAll the information necessary for working with monorepo can be found in this [article](https://vladimirgorej.com/blog/things-i-have-learned-maintaining-javascript-monorepo-with-lerna/).\n\n[Node.js](https://nodejs.org/) `\u003e=24.10.0` and `npm \u003e=11.6.1`\nare the minimum required versions that this repo runs on, but we recommend using the latest version of Node.js@24.\n\n### Setting up\n\nRun the following commands to setup the repository for local development:\n\n```shell\n $ git clone https://github.com/speclynx/apidom.git\n $ cd apidom\n $ npm i\n $ npm run build\n```\n\n### Setting up via docker\n\nThere are situations when satisfying all setup requirements of this repository on your local\ndevelopment machine is just not possible. In that case, you can use **docker** to get around it.\nRepository directory is mounted as volume inside a running container called `apidom-dev`.\nThat way you can edit code locally on your development machine and run **npm scripts**\ninside the `apidom-dev` docker container.\n\n**Build the ApiDOM docker image:**\n\n```sh\n $ git clone https://github.com/speclynx/apidom.git\n $ cd apidom\n $ docker-compose up\n```\n\n**Install dependencies and build ApiDOM inside the docker container:**\n\n```sh\n$ docker exec -it apidom-dev npm i --verbose\n$ docker exec -it apidom-dev npm run build\n```\n\n**Run npm scripts inside the docker container:**\n\n```sh\n$ docker exec -it apidom-dev npm run test\n```\n\n\u003e Note: monorepo needs to be build in order for monorepo package topology to work correctly.\n\n### Setting up via GitHub Codespaces\n\nThis repository is [configured](https://github.com/speclynx/apidom/tree/main/.devcontainer) to work with [GitHub Codespaces](https://github.com/codespaces).\nCreate a new codespace by picking this repository from the list of available repositories.\nOnce the codespace is created, run following commands inside the codespace terminal:\n\n```sh\n $ npm i\n $ npm run build\n```\n\n### npm scripts\n\nSome npm scripts run in parallel. Default maximum parallelization is set `2`. This is due to the fact\nthat our `CI` runs on GitHub Actions which uses GitHub hosted runners with [2-core CPUs](https://docs.github.com/en/actions/using-github-hosted-runners/about-github-hosted-runners#supported-runners-and-hardware-resources).\nIf you have computer with more than 2 CPU cores, you can speed running npm scripts by\ncreating an environment variable called `CPU_CORES` and assign it a number of your CPU cores.\n\nAssuming 4 CPU cores are available:\n\n```sh\n  $ export CPU_CORES=4\n  $ npm run build\n```\n\n`build` scripts now runs much faster than before.\n\n**Build artifacts**\n\n```sh\n $ npm run build\n```\n\n**Test**\n\nYou must first **build the artifacts** before running tests.\n\n```sh\n $ npm run test\n```\n\n**Lint**\n\n```sh\n $ npm run lint\n```\n\n**Check TypeScript types**\n\n```sh\n $ npm run typescript:check-types\n```\n\n**Generate TypeScript types**\n\n```sh\n $ npm run typescript:declaration\n```\n\n**Clean**\n\n```sh\n $ npm run clean\n```\n\n### Build artifacts\n\nAll the packages have identical build system and expose build artifacts in identical way.\nAfter building artifacts, every package will contain five (5) additional directories.\nAll the build artifacts are polymorphic - they can run in different environments like [Web Browser](https://en.wikipedia.org/wiki/Web_browser), [Node.js](https://nodejs.org/) or [Web Worker](https://developer.mozilla.org/en-US/docs/Web/API/Web_Workers_API).\n\n***.cjs**\n\nThese files are generated inside `src/` directory.\nContain ES5 compatible code with [CommonJS](https://en.wikipedia.org/wiki/CommonJS) style imports.\nThese build fragments are ideal for legacy [Node.js](https://nodejs.org/) and similar environments.\n\n***.mjs**\n\nThese files are generated inside `src/` directory.\nContain ES5 compatible code with [ES6 imports](https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Statements/import).\nThese build fragments are ideal for modern [Node.js](https://nodejs.org/),\nbundling with [Webpack](https://webpack.js.org/) or similar bundlers.\n\n**dist/**\n\nThis directory contains bundled build fragments that use [UMD](https://github.com/umdjs/umd) modules.\nThey're ideal for browser usage. The fragments are both in minified and un-minified form.\n\n**types/**\n\nTypeScript types generated from the source code.\n\n### Using this monorepo as a local dev dependency\n\nFor using this monorepo as a local dev dependency for `dependent project`,\nfollowing commands needs to be issued inside the monorepo directory after\nit has been cloned to a local filesystem:\n\n```sh\n $ npm i\n $ npm run build\n $ npm run link\n```\nThis will install the dependencies, built the monorepo and link all it's packages to\nglobal `node_modules`.\n\n#### Usage in `dependent project`\n\nNow that we have monorepo packages globally linked we can use them in `dependent project`.\nLet's say `dependent project` needs to directly use following packages:\n\n- @speclynx/apidom-traverse\n- @speclynx/apidom-core\n\nIssuing following command from inside the `dependent project` will link these packages:\n\n```sh\n $ npm link @speclynx/apidom-traverse @speclynx/apidom-core\n```\n\nIf more packages (or all of them) need to be used in `dependent project`, they need to be explicitly\nenumerated using above command and separated by single empty space.\n\nNotice that we link packages using single `npm link` command. This is necessary\nbecause of how `npm link` works internally. Always use single `npm link` command with\nmultiple package names as argument.\n\n**Don't ever do this!**\n\n```sh\n $ npm link @speclynx/apidom-traverse\n $ npm link @speclynx/apidom-core\n```\n\n\u003e Setting up npm script in `dependent project` can help keep things DRY.\n\n#### Cleaning up\n\n##### Dependent project\n\nThe best way to unlink monorepo packages from `dependent project` is to run following command\ninside the `dependent project`:\n\n```shell\n $ npm i\n```\n\nRunning `npm i` will remove the links to monorepo packages and install the packages from npm registry.\n\n\u003e Note: running `npm unlink \u003cpackage-name\u003e` in `dependent project` will remove the link to monorepo package,\nbut will leave the `dependent project` node_modules in corrupted state as there is no version of the package\ninstalled anymore. Running `npm i` is always a prefered way to restore your node_modules to original state.\n\n\n##### ApiDOM monorepo\n\nIt is not necessary to unlink monorepo packages from global `node_modules`. But if you\nwant to keep your global `node_modules` tidy you can run the following command in monorepo directory:\n\n```shell\n $ npm run unlink\n```\n\nRunning above npm script will unlink all monorepo packages from global `node_modules`.\n\nIf you want to just unlink particular monorepo packages, you have to enumerate them explicitly:\n\n```shell\n $ npm unlink --global @speclynx/apidom-traverse @speclynx/apidom-core\n```\n\n## Documentation\n\nIf there is one thing API description languages have taught us, it is that a single contract provides\nthe best and fastest way to design and iterate on an API. Developers building the API can move independently\nas they progress towards the defined contract found in the OpenAPI or RAML document.\nConversely, API consumers can build tools for consuming the API based on the API definition document.\n\nThis same pattern has proven to be just as valuable for building API description languages and tooling.\nApiDOM is the contract for producing and consuming the many API description languages and serialization formats\nand allows everyone to move quickly and independently.\n\n### What is an Element ?\n\nApiDOM is made up of many small elements that have a rich semantic meaning given their value and context.\nAn element is an individual piece that makes up an API, and can range from defining a resource to providing\nan example of an HTTP request.\n\nThe ApiDOM defines elements to be used for:\n\nDescribing an API\nDescribing data structures used within that API\nDescribing parse results when parsing API-related documents\nThese elements also seek to provide a way to decouple APIs and their semantics from the implementation details.\n\nThe structure of an ApiDOM is recursive by nature. When looking for specific elements,\nit is best to traverse the ApiDOM tree to look for a match. Querying the ApiDOM tree will\ndecouple our code from specific API description language. Also, it decouples our code from the\nspecific structure of these documents as long as they are semantically equivalent.\n\n### As a way to annotate JSON\n\nApiDOM provides the ability to take a normal JSON structure and add a layer on top of it for the purpose\nof annotating and adding semantic data. Instead of creating an entirely different structure to describe the data,\nApiDOM's approach is to expand the existing structure (we call it \"refracting\" a structure).\nHere is an example to show our point.\n\nTake the following simple JSON object.\n\n```json\n{\n  \"name\": \"John Doe\",\n  \"email\": \"john@example.com\"\n}\n```\n\nUsing ApiDOM, we can expand this out and add some human-readable titles and descriptions.\n\n```json\n{\n  \"element\": \"object\",\n  \"content\": [\n    {\n      \"element\": \"member\",\n      \"meta\": {\n        \"title\": \"Name\",\n        \"description\": \"Name of a person\"\n      },\n      \"content\": {\n        \"key\": {\n          \"element\": \"string\",\n          \"content\": \"name\"\n        },\n        \"value\": {\n          \"element\": \"string\",\n          \"content\": \"John Doe\"\n        }\n      }\n    },\n    {\n      \"element\": \"member\",\n      \"meta\": {\n        \"title\": \"Email\",\n        \"description\": \"Email address for the person\"\n      },\n      \"content\": {\n        \"key\": {\n          \"element\": \"string\",\n          \"content\": \"email\"\n        },\n        \"value\": {\n          \"element\": \"string\",\n          \"content\": \"john@example.com\"\n        }\n      }\n    }\n  ]\n}\n```\n\nWe added some semantic data to the existing data, but we did so while retaining the semantic structure of the data\nwith the object and string elements. **This means there is no semantic difference in the ApiDOM structure and\nthe original JSON structure**. It also means we can add extra semantics on top of these structural ones.\n\n### As a unifying structure\n\nYou may have noticed the similarities between the JSON example above and XML.\nXML has elements, attributes, and content. It would be a good question to ask if we simply turned JSON into XML.\n\nApiDOM is actually meant to provide these cross-format similarities. It means that a JSON structure\nmay be refracted and converted to XML. It also means an XML document may be converted into ApiDOM.\nThis also goes for YAML, HTML, CSV, and many other formats. ApiDOM is a way to use refracting to unify these structures.\n\nLet's look at another example, this time refacting XML with ApiDOM.\n\n```xml\n\u003cperson name=\"John Doe\" email=\"john@example.com\"\u003e\u003c/person\u003e\n```\n\nThis example in refracted form would look like the following snippet. Notice that we're using attributes in resulting ApiDOM structure.\n\n```json\n{\n  \"element\": \"person\",\n  \"attributes\": {\n    \"name\": {\n      \"element\": \"string\",\n      \"content\": \"John Doe\"\n    },\n    \"email\": {\n      \"element\": \"string\",\n      \"content\": \"john@example.com\"\n    }\n  }\n}\n```\n\nSince we can go back and forth between JSON, YAML, XML, and other formats, we are now able to use same toolset across the different formats.\nThat means we could use XSLT to transform JSON documents.\n\n### As a queryable structure\n\nApiDOM is meant to free us from the structure of our documents, similar to how XML does with things\nlike XPATH or the DOM. It means we can now query JSON documents as if there was an underlying DOM,\nwhich decouples our SDK from our structure and our structure from our data.\n\n### ApiDOM stages\n\nThere are three stages to ApiDOM\n\n- Parse stage\n- Refract stage\n- Generate stage\n\n\n#### Parse stage\n\nThe parse stage takes JSON string and produces ApiDOM structure using the base ApiDOM namespace. There are two phases of parsing:\n\n- Lexical Analysis phase\n- Syntactic Analysis phase\n\n\n##### Lexical Analysis phase\n\nLexical Analysis will take a JSON string and turn it into a stream of tokens. tree-sitter / web-tree-sitter is used\nas an underlying lexical analyzer.\n\n##### Syntactic Analysis\n\nSyntactic Analysis will take a stream of tokens and turn it into an ApiDOM representation.\nCST produced by lexical analysis is syntactically analyzed, and ApiDOM structure using base (generic) ApiDOM namespace is produced.\nSyntactic analysis can further be direct or indirect. JSON parser has both direct and indirect syntactical analyzers,\nbut YAML parser only has an indirect one.\n\n###### Direct Syntactical analysis\n\nThis analysis directly turns tree-sitter CST into ApiDOM. Single traversal is required, which makes it super performant,\nand it's the default analysis used.\n\n###### Indirect Syntactic analysis\n\nThis analysis turns trees-sitter CST into YAML AST representation. Then YAML AST is turned into ApiDOM.\nTwo traversals are required, which makes the indirect analysis less performant than the direct one.\nThough less performant, having YAML AST representation allows us to do further complex AST analysis.\n\n#### Refract stage\n\nThe refract stage takes a generic ApiDOM structure (base namespace) and traverses through it, adding, updating,\nand removing nodes as it goes along and turning it into semantic ApiDOM structure (like OpenAPI or AsyncAPI).\nThis is by far the most complex part of ApiDOM. This is where plugins operate.\nIf plugins are used, additional traversal is currently needed.\n\n#### Generate stage\n\nWe can currently only generate JSON documents from the ApiDOM structure.\nIt doesn't matter if the original document was originally defined in JSON or YAML.\nGenerated JSON documented will have exactly the same semantic information as the original one,\nbut the style information from the original document is not preserved (white spaces/comments, etc..).\n\n---\n\nHaving said that, this is how JSON OpenAPI 3.1 document gets transformed into ApiDOM:\n\n\n**with direct syntactic analysis (requires 2 traversals)**\n```\nJSON string -\u003e tree-sitter CST -\u003e  generic ApiDOM -\u003e OpenAPI 3.1 ApiDOM\n```\n\n**with indirect syntactic analysis (requires 3 traversals)**\n```\nJSON string -\u003e tree-sitter CST -\u003e JSON AST -\u003e generic ApiDOM -\u003e OpenAPI 3.1 ApiDOM\n```\n\n**with direct syntactic analysis and additional plugins (requires 3 traversal)**\n```\nJSON string -\u003e tree-sitter CST -\u003e generic ApiDOM -\u003e OpenAPI 3.1 ApiDOM -\u003e plugins -\u003e OpenAPI 3.1 ApiDOM\n```\n---\n\nThis very closely reflects how [Babel](https://github.com/babel/babel) works ([Babel Plugin Handbook](https://github.com/jamiebuilds/babel-handbook/blob/master/translations/en/plugin-handbook.md)).\nTheir transform phase is our refract phase. The only difference is that when plugins are involved, our transform phase\nrequires 2 traversals instead of a single one. We can find a way in the future how to fold these 2 traversals into a single one.\n\n## License\n\nApiDOM is licensed under [Apache 2.0 license](https://github.com/speclynx/apidom/blob/main/LICENSES/Apache-2.0.txt).\nApiDOM comes with an explicit [NOTICE](https://github.com/speclynx/apidom/blob/main/NOTICE) file\ncontaining additional legal notices and information.\n\nThis project uses [REUSE specification](https://reuse.software/spec/) that defines a standardized method\nfor declaring copyright and licensing for software projects.\n\n## Software Bill Of Materials (SBOM)\n\nSoftware Bill Of materials is available in this repository [dependency graph](https://github.com/speclynx/apidom/network/dependencies).\nClick on `Export SBOM` button to download the SBOM in [SPDX format](https://spdx.dev/).\n\n","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fspeclynx%2Fapidom","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fspeclynx%2Fapidom","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fspeclynx%2Fapidom/lists"}