Skip to content

Commit 2826c46

Browse files
authoredMar 19, 2024
feat(codegen): expose referenced type as hidden symbol (#6008)
1 parent 3742b3f commit 2826c46

File tree

4 files changed

+39
-1
lines changed

4 files changed

+39
-1
lines changed
 

‎packages/@sanity/codegen/src/typescript/__tests__/__snapshots__/typeGenerator.test.ts.snap

+5
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
// Jest Snapshot v1, https://goo.gl/fbAQLP
22

3+
exports[`generateSchemaTypes can generate well known types 1`] = `"export declare const internalGroqTypeReferenceTo: unique symbol;"`;
4+
35
exports[`generateSchemaTypes generateTypeNodeTypes should be able to generate types for type nodes: boolean 1`] = `"export type test_2 = boolean;"`;
46

57
exports[`generateSchemaTypes generateTypeNodeTypes should be able to generate types for type nodes: null 1`] = `"export type test_5 = null;"`;
@@ -30,9 +32,11 @@ export type Post = {
3032
author?: {
3133
_ref: string;
3234
_weak?: boolean;
35+
[internalGroqTypeReferenceTo]?: \\"author\\";
3336
} | {
3437
_ref: string;
3538
_weak?: boolean;
39+
[internalGroqTypeReferenceTo]?: \\"ghost\\";
3640
};
3741
slug?: Slug;
3842
excerpt?: string;
@@ -41,6 +45,7 @@ export type Post = {
4145
asset: {
4246
_ref: string;
4347
_weak?: boolean;
48+
[internalGroqTypeReferenceTo]?: \\"sanity.imageAsset\\";
4449
};
4550
caption?: string;
4651
attribution?: string;

‎packages/@sanity/codegen/src/typescript/__tests__/typeGenerator.test.ts

+7
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,12 @@ describe('generateSchemaTypes', () => {
2424
expect(typeDeclarations).toMatchSnapshot()
2525
})
2626

27+
test('can generate well known types', async () => {
28+
const typeDeclarations = TypeGenerator.generateKnownTypes()
29+
30+
expect(typeDeclarations).toMatchSnapshot()
31+
})
32+
2733
test('should generate correct types for document schema with string fields', () => {
2834
const schema: SchemaType = [
2935
{
@@ -247,6 +253,7 @@ describe('generateSchemaTypes', () => {
247253
_ref: string;
248254
_type: \\"reference\\";
249255
_weak?: boolean;
256+
[internalGroqTypeReferenceTo]?: \\"author\\";
250257
};
251258
};
252259

‎packages/@sanity/codegen/src/typescript/typeGenerator.ts

+23
Original file line numberDiff line numberDiff line change
@@ -11,6 +11,8 @@ import {
1111
type UnionTypeNode,
1212
} from 'groq-js'
1313

14+
const REFERENCE_SYMBOL_NAME = 'internalGroqTypeReferenceTo'
15+
1416
/**
1517
* A class used to generate TypeScript types from a given schema
1618
* @internal
@@ -71,6 +73,18 @@ export class TypeGenerator {
7173
return new CodeGenerator(t.exportNamedDeclaration(typeAlias)).generate().code
7274
}
7375

76+
static generateKnownTypes(): string {
77+
const typeOperator = t.tsTypeOperator(t.tsSymbolKeyword())
78+
typeOperator.operator = 'unique'
79+
80+
const identifier = t.identifier(REFERENCE_SYMBOL_NAME)
81+
identifier.typeAnnotation = t.tsTypeAnnotation(typeOperator)
82+
83+
const decleration = t.variableDeclaration('const', [t.variableDeclarator(identifier)])
84+
decleration.declare = true
85+
return new CodeGenerator(t.exportNamedDeclaration(decleration)).generate().code
86+
}
87+
7488
/**
7589
* Since we are sanitizing identifiers we migt end up with collisions. Ie there might be a type mux.video and muxVideo, both these
7690
* types would be sanityized into MuxVideo. To avoid this we keep track of the generated type names and add a index to the name.
@@ -204,6 +218,15 @@ export class TypeGenerator {
204218
}
205219
}
206220
}
221+
if (typeNode.dereferencesTo !== undefined) {
222+
const derefType = t.tsPropertySignature(
223+
t.identifier(REFERENCE_SYMBOL_NAME),
224+
t.tsTypeAnnotation(t.tsLiteralType(t.stringLiteral(typeNode.dereferencesTo))),
225+
)
226+
derefType.computed = true
227+
derefType.optional = true
228+
props.push(derefType)
229+
}
207230
return t.tsTypeLiteral(props)
208231
}
209232

‎packages/sanity/src/_internal/cli/threads/codegenGenerateTypes.ts

+4-1
Original file line numberDiff line numberDiff line change
@@ -58,7 +58,10 @@ async function main() {
5858
const schema = await readSchema(opts.schemaPath)
5959

6060
const typeGenerator = new TypeGenerator(schema)
61-
const schemaTypes = typeGenerator.generateSchemaTypes()
61+
const schemaTypes = [
62+
typeGenerator.generateSchemaTypes(),
63+
TypeGenerator.generateKnownTypes(),
64+
].join('\n')
6265
const resolver = getResolver()
6366

6467
parentPort?.postMessage({

0 commit comments

Comments
 (0)
Please sign in to comment.