Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Explore Options for CALM Schema to TypeScript Generation - Library Evaluation #701

Open
LeighFinegold opened this issue Dec 24, 2024 · 1 comment · May be fixed by #702
Open

Explore Options for CALM Schema to TypeScript Generation - Library Evaluation #701

LeighFinegold opened this issue Dec 24, 2024 · 1 comment · May be fixed by #702

Comments

@LeighFinegold
Copy link
Member

Feature Request

Description of Problem:

There are many use cases for the CALM (Common Architecture Language Model) language, such as generating architecture implementation files (#444), documentation (#478), and more. Since the CALM specification is defined using JSON Schema, it is often necessary to convert the CALM model into strongly typed representations, making it easier to manipulate and use for generating code outputs or documentation.

Currently, there is no clear or standardised approach for converting CALM schemas (JSON Schema) into usable TypeScript types. It should consider the potential for extension.

Potential Solutions:

  1. Define our own internal model manually: We could parse the CALM schema into a custom internal model, but this would require significant time and effort to implement and maintain.

  2. Use an existing JSON Schema to TypeScript generator: We could leverage an established npm library (such as json-schema-to-typescript ) to automatically generate TypeScript types from the CALM schemas. This approach would save time and reduce the complexity of creating a custom solution, but it may not always be a perfect fit for CALM’s unique and extension needs.

  3. Write our own TypeScript generator: We could write our own custom generator (AST) tailored specifically to the CALM schema. While this would give us the most control, it would also require significant effort to develop and maintain, as well as deal with any edge cases specific to CALM.

Focus of this Issue

This issue will focus on Solution 2. Will explore json-schema-to-typescript which seems the most widely adopted npm library for JSON Schema to TypeScript conversion, as it is the most straightforward and efficient approach to meet our needs. We want to evaluate whether this approach will work effectively with CALM schemas and whether there are any limitations or modifications needed to integrate it fully into our toolchain.

LeighFinegold pushed a commit to LeighFinegold/architecture-as-code that referenced this issue Dec 24, 2024
LeighFinegold added a commit to LeighFinegold/architecture-as-code that referenced this issue Dec 24, 2024
@LeighFinegold
Copy link
Member Author

LeighFinegold commented Dec 24, 2024

Linked to this issue is a PR containing a basic setup of the library to generate models

The library seems a little buggy when it comes to generating type definitions for defs that are not referenced via any schemas. I checked in generated output even though if we were to use, this would not be necessary.

Some observations/questions that arose from this poc:-

  1. Do we have the schema types defined well enough? Perhaps core.json should contain node, relationship, , but there should be separate architecture and patterns schemas referencing those.
  2. The library struggles with pattern field concepts in json schema
  3. Under the covers it uses json-schema-ref-parser and that is a library which has mechanisms for bundling, parsing and deferencing schemas inline - something that could be useful as part of building docify on Create an Architecture Documentation Website from CALM #478)
  4. It helped highlight that perhaps our oneOf syntax around relationship-type was not quite right i.e. you don't need to define properties section. See https://json-schema.org/learn/json-schema-examples. See relationship-type model question at end
  5. Although it didn't impact it for local testing, I can see some of the typescript tries to parse the schema into v4 which is not what we are using)
function parseAsJSONSchema(filename: string): JSONSchema4 {
  const contents = Try(
    () => readFileSync(filename),
    () => {
      throw new ReferenceError(`Unable to read file "${filename}"`)
    },
  )
  return parseFileAsJSONSchema(filename, contents.toString())
}

  1. AdditionalProperties = true will lead to
    [k: string]: unknown;

being added to every defintiion

Current Conclusion
My conclusion atm would be still that perhaps we do Option 1 or if more mature Option 3. (leveraging option 2 output to determine improvements in our spec - or work with the owner of the typescript library to enhance it to support all our cases). I feel like we need to simulate more how CALM could be extended.

Relationship Type Model Question

Do we want:-

export interface Relationship {
  "unique-id": string;
  description?: string;
  "relationship-type": ComposedOfType | InteractsType | ConnectsType | DeployedInType;

or

export interface Relationship {
  "unique-id": string;
  description?: string;
  "relationship-type": {
    interacts?: InteractsType;
    connects?: ConnectsType;
    "deployed-in"?: DeployedInType;
    "composed-of"?: ComposedOfType;
    [k: string]: unknown;
  };

The later being more inlined to what it is currently on main

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging a pull request may close this issue.

1 participant