Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 10 additions & 2 deletions .github/workflows/generate-models.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -17,12 +17,12 @@ jobs:

steps:
- name: Checkout
uses: actions/checkout@v2
uses: actions/checkout@v4
with:
path: models-lib

- name: Use Node.js 18.17.1
uses: actions/setup-node@v1
uses: actions/setup-node@v4
with:
node-version: 18.17.1

Expand All @@ -37,3 +37,11 @@ jobs:
run: npm start -- generate ${{ matrix.language }} --destination ../output/
working-directory: models-lib

# Generate the TypeScript models from this ref inside models-ts, then build and test them there,
# so that changes which produce invalid TypeScript are caught before they reach models-ts
test-ts:
needs: generate
uses: openactive/models-ts/.github/workflows/create-data-model-pr.yaml@main
with:
models-lib_ref: ${{ github.ref }}

26 changes: 26 additions & 0 deletions src/generators/typescript/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -58,6 +58,32 @@ class TypeScript extends Generator {
return true;
}

/**
* The value of `@type` that identifies this model in JSON-LD data.
*
* OpenActive and schema.org types are written without a prefix, because the OpenActive context defines terms for
* OpenActive types and uses schema.org as its `@vocab`. Types from extensions (e.g. `beta:Bar` or
* `test:OpenBookingSimulateAction`) are only reachable through their extension's prefix, so the prefix is kept.
*
* @param {Model} model
*/
getJsonLdTypeName(model) {
const prefix = this.getPrefix(model.type);
if (prefix && prefix !== 'schema') {
return model.type;
}
return this.getPropNameFromFQP(model.type);
}

createModelData(model, extensions) {
const data = super.createModelData(model, extensions);
return {
...data,
/** e.g. Place, Thing, beta:Bar */
jsonLdTypeName: this.getJsonLdTypeName(model),
};
}

async renderModel(data) {
this.modelTemplate =
this.modelTemplate ||
Expand Down
4 changes: 2 additions & 2 deletions src/generators/typescript/model.ts.mustache
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import * as schema from '../schema';
{{/classDoc}}
*/
export type {{{ className }}} = {
'@type': '{{{ modelTypePropName }}}';
'@type': '{{{ jsonLdTypeName }}}';
'@context'?: string | string[];
{{#fieldList}}
{{#if description }}
Expand Down Expand Up @@ -58,7 +58,7 @@ export type {{{ className }}}OrSubClass =
{{/classDoc}}
*/
export const {{{ className }}}JoiSchema = Joi.object({
'@type': Joi.string().valid('{{{ modelTypePropName }}}').required(),
'@type': Joi.string().valid('{{{ jsonLdTypeName }}}').required(),
'@context': Joi.alternatives().try([Joi.string(), Joi.array().items(Joi.string())]),
{{#fieldList}}
{{{ renderMemberName }}}: {{{ propertyJoiType }}},
Expand Down
Loading