7
7
* subject to an additional IP rights grant found at
8
8
* http://polymer.github.io/PATENTS.txt
9
9
*/
10
- import { Schema2Base , ClassGenerator } from './schema2base.js' ;
10
+ import { Schema2Base , ClassGenerator , AddFieldOptions } from './schema2base.js' ;
11
11
import { SchemaNode } from './schema2graph.js' ;
12
12
import { ParticleSpec } from '../runtime/particle-spec.js' ;
13
13
import minimist from 'minimist' ;
@@ -28,10 +28,10 @@ const keywords = [
28
28
] ;
29
29
30
30
const typeMap = {
31
- 'T' : { type : 'String' , decodeFn : 'decodeText()' , defaultVal : `""` } ,
32
- 'U' : { type : 'String' , decodeFn : 'decodeText()' , defaultVal : `""` } ,
33
- 'N' : { type : 'Double' , decodeFn : 'decodeNum()' , defaultVal : '0.0' } ,
34
- 'B' : { type : 'Boolean' , decodeFn : 'decodeBool()' , defaultVal : 'false' } ,
31
+ 'T' : { type : 'String' , decodeFn : 'decodeText()' , defaultVal : `""` , schemaType : 'FieldType.Text' } ,
32
+ 'U' : { type : 'String' , decodeFn : 'decodeText()' , defaultVal : `""` , schemaType : 'FieldType.Text' } ,
33
+ 'N' : { type : 'Double' , decodeFn : 'decodeNum()' , defaultVal : '0.0' , schemaType : 'FieldType.Number' } ,
34
+ 'B' : { type : 'Boolean' , decodeFn : 'decodeBool()' , defaultVal : 'false' , schemaType : 'FieldType.Boolean' } ,
35
35
} ;
36
36
37
37
export class Schema2Kotlin extends Schema2Base {
@@ -54,7 +54,14 @@ package ${this.scope}
54
54
// Current implementation doesn't support references or optional field detection
55
55
56
56
import arcs.sdk.*
57
- ${ this . opts . wasm ? 'import arcs.sdk.wasm.*' : 'import arcs.core.storage.api.toPrimitiveValue\nimport arcs.core.data.RawEntity\nimport arcs.core.data.util.toReferencable\nimport arcs.core.data.util.ReferencablePrimitive' }
57
+ ${ this . opts . wasm ?
58
+ `import arcs.sdk.wasm.*` :
59
+ `\
60
+ import arcs.sdk.Entity
61
+ import arcs.core.data.*
62
+ import arcs.core.data.util.toReferencable
63
+ import arcs.core.data.util.ReferencablePrimitive
64
+ import arcs.core.storage.api.toPrimitiveValue` }
58
65
` ;
59
66
}
60
67
@@ -130,7 +137,7 @@ abstract class Abstract${particleName} : ${this.opts.wasm ? 'WasmParticleImpl' :
130
137
}
131
138
}
132
139
133
- class KotlinGenerator implements ClassGenerator {
140
+ export class KotlinGenerator implements ClassGenerator {
134
141
fields : string [ ] = [ ] ;
135
142
fieldVals : string [ ] = [ ] ;
136
143
setFields : string [ ] = [ ] ;
@@ -144,11 +151,13 @@ class KotlinGenerator implements ClassGenerator {
144
151
fieldSerializes : string [ ] = [ ] ;
145
152
fieldDeserializes : string [ ] = [ ] ;
146
153
fieldsForToString : string [ ] = [ ] ;
154
+ singletonSchemaFields : string [ ] = [ ] ;
155
+ collectionSchemaFields : string [ ] = [ ] ;
147
156
148
157
constructor ( readonly node : SchemaNode , private readonly opts : minimist . ParsedArgs ) { }
149
158
150
159
// TODO: allow optional fields in kotlin
151
- addField ( field : string , typeChar : string , isOptional : boolean , refClassName : string | null ) {
160
+ addField ( { field, typeChar, refClassName , isOptional = false , isCollection = false } : AddFieldOptions ) {
152
161
// TODO: support reference types in kotlin
153
162
if ( typeChar === 'R' ) return ;
154
163
@@ -181,6 +190,46 @@ class KotlinGenerator implements ClassGenerator {
181
190
this . fieldSerializes . push ( `"${ field } " to ${ fixed } .toReferencable()` ) ;
182
191
this . fieldDeserializes . push ( `${ fixed } = data.singletons["${ fixed } "].toPrimitiveValue(${ type } ::class, ${ defaultVal } )` ) ;
183
192
this . fieldsForToString . push ( `${ fixed } = $${ fixed } ` ) ;
193
+ if ( isCollection ) {
194
+ this . collectionSchemaFields . push ( `"${ field } " to ${ typeMap [ typeChar ] . schemaType } ` ) ;
195
+ } else {
196
+ this . singletonSchemaFields . push ( `"${ field } " to ${ typeMap [ typeChar ] . schemaType } ` ) ;
197
+ }
198
+ }
199
+
200
+ mapOf ( items : string [ ] ) : string {
201
+ switch ( items . length ) {
202
+ case 0 :
203
+ return `emptyMap()` ;
204
+ case 1 :
205
+ return `mapOf(${ items [ 0 ] } )` ;
206
+ default :
207
+ return `\
208
+ mapOf(
209
+ ${ this . leftPad ( items . join ( ',\n' ) , 4 ) }
210
+ )` ;
211
+ }
212
+
213
+ }
214
+
215
+ createSchema ( schemaHash : string ) : string {
216
+ const schemaNames = this . node . schema . names . map ( n => `SchemaName("${ n } ")` ) ;
217
+ return `\
218
+ Schema(
219
+ listOf(${ schemaNames . join ( ',\n' + ' ' . repeat ( 8 ) ) } ),
220
+ SchemaFields(
221
+ singletons = ${ this . leftPad ( this . mapOf ( this . singletonSchemaFields ) , 8 , true ) } ,
222
+ collections = ${ this . leftPad ( this . mapOf ( this . collectionSchemaFields ) , 8 , true ) }
223
+ ),
224
+ "${ schemaHash } "
225
+ )` ;
226
+ }
227
+
228
+ leftPad ( input : string , indent : number , skipFirst : boolean = false ) {
229
+ return input
230
+ . split ( '\n' )
231
+ . map ( ( line : string , idx : number ) => ( idx === 0 && skipFirst ) ? line : ' ' . repeat ( indent ) + line )
232
+ . join ( '\n' ) ;
184
233
}
185
234
186
235
generate ( schemaHash : string , fieldCount : number ) : string {
@@ -256,7 +305,18 @@ ${this.opts.wasm ? `
256
305
}
257
306
258
307
class ${ name } _Spec() : ${ this . getType ( 'EntitySpec' ) } <${ name } > {
308
+ ${ this . opts . wasm ? '' : `\
259
309
310
+ companion object {
311
+ val schema = ${ this . leftPad ( this . createSchema ( schemaHash ) , 8 , true ) }
312
+
313
+ init {
314
+ SchemaRegistry.register(schema)
315
+ }
316
+ }
317
+
318
+ override fun schema() = schema
319
+ ` }
260
320
override fun create() = ${ name } ()
261
321
${ ! this . opts . wasm ? `
262
322
override fun deserialize(data: RawEntity): ${ name } {
0 commit comments