@@ -618,17 +618,18 @@ export class TsSchemaGenerator {
618618 ts . factory . createPropertyAssignment (
619619 field . name ,
620620 ts . factory . createObjectLiteralExpression ( [
621- ts . factory . createPropertyAssignment (
622- 'type' ,
623- ts . factory . createStringLiteral ( field . type . type ! ) ,
624- ) ,
621+ ts . factory . createPropertyAssignment ( 'type' , this . generateFieldTypeLiteral ( field ) ) ,
625622 ] ) ,
626623 ) ,
627624 ) ;
628625 }
629626 }
630627
631628 // model-level id and unique
629+
630+ // it's possible to have the same set of fields in both `@@id` and `@@unique`
631+ // so we need to deduplicate them
632+ const seenKeys = new Set < string > ( ) ;
632633 for ( const attr of dm . attributes ) {
633634 if ( attr . decl . $refText === '@@id' || attr . decl . $refText === '@@unique' ) {
634635 const fieldNames = this . getReferenceNames ( attr . args [ 0 ] ! . value ) ;
@@ -643,15 +644,17 @@ export class TsSchemaGenerator {
643644 ts . factory . createPropertyAssignment (
644645 fieldNames [ 0 ] ! ,
645646 ts . factory . createObjectLiteralExpression ( [
646- ts . factory . createPropertyAssignment (
647- 'type' ,
648- ts . factory . createStringLiteral ( fieldDef . type . type ! ) ,
649- ) ,
647+ ts . factory . createPropertyAssignment ( 'type' , this . generateFieldTypeLiteral ( fieldDef ) ) ,
650648 ] ) ,
651649 ) ,
652650 ) ;
653651 } else {
654652 // multi-field unique
653+ const key = fieldNames . join ( '_' ) ;
654+ if ( seenKeys . has ( key ) ) {
655+ continue ;
656+ }
657+ seenKeys . add ( key ) ;
655658 properties . push (
656659 ts . factory . createPropertyAssignment (
657660 fieldNames . join ( '_' ) ,
@@ -663,7 +666,7 @@ export class TsSchemaGenerator {
663666 ts . factory . createObjectLiteralExpression ( [
664667 ts . factory . createPropertyAssignment (
665668 'type' ,
666- ts . factory . createStringLiteral ( fieldDef . type . type ! ) ,
669+ this . generateFieldTypeLiteral ( fieldDef ) ,
667670 ) ,
668671 ] ) ,
669672 ) ;
@@ -678,6 +681,11 @@ export class TsSchemaGenerator {
678681 return ts . factory . createObjectLiteralExpression ( properties , true ) ;
679682 }
680683
684+ private generateFieldTypeLiteral ( field : DataModelField ) : ts . Expression {
685+ invariant ( field . type . type || field . type . reference , 'Field type must be a primitive or reference' ) ;
686+ return ts . factory . createStringLiteral ( field . type . type ?? field . type . reference ! . $refText ) ;
687+ }
688+
681689 private createEnumObject ( e : Enum ) {
682690 return ts . factory . createObjectLiteralExpression (
683691 e . fields . map ( ( field ) =>
0 commit comments