cddl 0.14.10 → 0.15.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/build/index.d.ts CHANGED
@@ -7,4 +7,5 @@ declare const _default: {
7
7
  export default _default;
8
8
  export { Lexer, Parser };
9
9
  export * from './ast.js';
10
+ export * from './utils.js';
10
11
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,YAAY,CAAA;AAC9B,OAAO,MAAM,MAAM,aAAa,CAAA;AAEhC,wBAAgB,KAAK,CAAE,QAAQ,EAAE,MAAM,mCAGtC;;;;AAED,wBAAwB;AACxB,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,CAAA;AACxB,cAAc,UAAU,CAAA"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,MAAM,YAAY,CAAA;AAC9B,OAAO,MAAM,MAAM,aAAa,CAAA;AAEhC,wBAAgB,KAAK,CAAE,QAAQ,EAAE,MAAM,mCAGtC;;;;AAED,wBAAwB;AACxB,OAAO,EAAE,KAAK,EAAE,MAAM,EAAE,CAAA;AACxB,cAAc,UAAU,CAAA;AACxB,cAAc,YAAY,CAAA"}
package/build/index.js CHANGED
@@ -7,3 +7,4 @@ export function parse(filePath) {
7
7
  export default { parse };
8
8
  export { Lexer, Parser };
9
9
  export * from './ast.js';
10
+ export * from './utils.js';
package/build/utils.d.ts CHANGED
@@ -1,7 +1,26 @@
1
+ import type { Assignment, Array as CDDLArray, Group, NativeTypeWithOperator, Property, PropertyReference, Variable } from './ast.js';
1
2
  import { Token } from './tokens.js';
2
3
  export declare function isLetter(ch: string): boolean;
3
4
  export declare function isAlphabeticCharacter(ch: string): boolean;
4
5
  export declare function isDigit(ch: string): boolean;
5
6
  export declare function hasSpecialNumberCharacter(ch: number): boolean;
6
7
  export declare function parseNumberValue(token: Token): string | number;
8
+ export declare function pascalCase(name: string): string;
9
+ export declare function isVariable(assignment: Assignment): assignment is Variable;
10
+ export declare function isGroup(t: any): t is Group;
11
+ export declare function isCDDLArray(t: any): t is CDDLArray;
12
+ export declare function isProperty(t: any): t is Property;
13
+ export declare function isUnNamedProperty(t: any): t is Property & {
14
+ Name: '';
15
+ };
16
+ export declare function isNamedGroupReference(t: any): t is PropertyReference & {
17
+ Value: string;
18
+ };
19
+ export declare function isPropertyReference(t: any): t is PropertyReference;
20
+ export declare function isNativeTypeWithOperator(t: any): t is NativeTypeWithOperator;
21
+ export declare function isRange(t: any): boolean;
22
+ export declare function isLiteralWithValue(t: any): t is {
23
+ Type: 'literal';
24
+ Value: unknown;
25
+ };
7
26
  //# sourceMappingURL=utils.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../src/utils.ts"],"names":[],"mappings":"AAAA,OAAO,EAAU,KAAK,EAAE,MAAM,aAAa,CAAA;AAE3C,wBAAgB,QAAQ,CAAE,EAAE,EAAE,MAAM,GAAG,OAAO,CAE7C;AAED,wBAAgB,qBAAqB,CAAE,EAAE,EAAE,MAAM,GAAG,OAAO,CAE1D;AAED,wBAAgB,OAAO,CAAE,EAAE,EAAE,MAAM,GAAG,OAAO,CAE5C;AAED,wBAAgB,yBAAyB,CAAE,EAAE,EAAE,MAAM,WAOpD;AAED,wBAAgB,gBAAgB,CAAE,KAAK,EAAE,KAAK,GAAG,MAAM,GAAG,MAAM,CAa/D"}
1
+ {"version":3,"file":"utils.d.ts","sourceRoot":"","sources":["../src/utils.ts"],"names":[],"mappings":"AAEA,OAAO,KAAK,EACR,UAAU,EACV,KAAK,IAAI,SAAS,EAClB,KAAK,EACL,sBAAsB,EACtB,QAAQ,EACR,iBAAiB,EACjB,QAAQ,EACX,MAAM,UAAU,CAAA;AAEjB,OAAO,EAAU,KAAK,EAAE,MAAM,aAAa,CAAA;AAE3C,wBAAgB,QAAQ,CAAE,EAAE,EAAE,MAAM,GAAG,OAAO,CAE7C;AAED,wBAAgB,qBAAqB,CAAE,EAAE,EAAE,MAAM,GAAG,OAAO,CAE1D;AAED,wBAAgB,OAAO,CAAE,EAAE,EAAE,MAAM,GAAG,OAAO,CAE5C;AAED,wBAAgB,yBAAyB,CAAE,EAAE,EAAE,MAAM,WAOpD;AAED,wBAAgB,gBAAgB,CAAE,KAAK,EAAE,KAAK,GAAG,MAAM,GAAG,MAAM,CAa/D;AAED,wBAAgB,UAAU,CAAE,IAAI,EAAE,MAAM,UAEvC;AAED,wBAAgB,UAAU,CAAE,UAAU,EAAE,UAAU,GAAG,UAAU,IAAI,QAAQ,CAE1E;AAED,wBAAgB,OAAO,CAAE,CAAC,EAAE,GAAG,GAAG,CAAC,IAAI,KAAK,CAE3C;AAED,wBAAgB,WAAW,CAAE,CAAC,EAAE,GAAG,GAAG,CAAC,IAAI,SAAS,CAEnD;AAED,wBAAgB,UAAU,CAAE,CAAC,EAAE,GAAG,GAAG,CAAC,IAAI,QAAQ,CAEjD;AAED,wBAAgB,iBAAiB,CAAE,CAAC,EAAE,GAAG,GAAG,CAAC,IAAI,QAAQ,GAAG;IAAE,IAAI,EAAE,EAAE,CAAA;CAAE,CAEvE;AAED,wBAAgB,qBAAqB,CAAE,CAAC,EAAE,GAAG,GAAG,CAAC,IAAI,iBAAiB,GAAG;IAAE,KAAK,EAAE,MAAM,CAAA;CAAE,CAEzF;AAED,wBAAgB,mBAAmB,CAAE,CAAC,EAAE,GAAG,GAAG,CAAC,IAAI,iBAAiB,CAEnE;AAED,wBAAgB,wBAAwB,CAAE,CAAC,EAAE,GAAG,GAAG,CAAC,IAAI,sBAAsB,CAE7E;AAED,wBAAgB,OAAO,CAAE,CAAC,EAAE,GAAG,GAAG,OAAO,CAExC;AAED,wBAAgB,kBAAkB,CAAE,CAAC,EAAE,GAAG,GAAG,CAAC,IAAI;IAC9C,IAAI,EAAE,SAAS,CAAA;IACf,KAAK,EAAE,OAAO,CAAA;CACjB,CAEA"}
package/build/utils.js CHANGED
@@ -1,3 +1,4 @@
1
+ import camelcase from 'camelcase';
1
2
  import { Tokens } from './tokens.js';
2
3
  export function isLetter(ch) {
3
4
  return 'a' <= ch && ch <= 'z' || 'A' <= ch && ch <= 'Z';
@@ -24,3 +25,36 @@ export function parseNumberValue(token) {
24
25
  }
25
26
  return parseInt(token.Literal, 10);
26
27
  }
28
+ export function pascalCase(name) {
29
+ return camelcase(name, { pascalCase: true });
30
+ }
31
+ export function isVariable(assignment) {
32
+ return assignment.Type === 'variable';
33
+ }
34
+ export function isGroup(t) {
35
+ return t && t.Type === 'group';
36
+ }
37
+ export function isCDDLArray(t) {
38
+ return t && t.Type === 'array';
39
+ }
40
+ export function isProperty(t) {
41
+ return t && typeof t.Name === 'string' && typeof t.HasCut === 'boolean';
42
+ }
43
+ export function isUnNamedProperty(t) {
44
+ return isProperty(t) && t.Name === '';
45
+ }
46
+ export function isNamedGroupReference(t) {
47
+ return isGroup(t) && isPropertyReference(t) && typeof t.Value === 'string';
48
+ }
49
+ export function isPropertyReference(t) {
50
+ return t && typeof t === 'object' && 'Value' in t;
51
+ }
52
+ export function isNativeTypeWithOperator(t) {
53
+ return t && typeof t.Type === 'object' && 'Operator' in t;
54
+ }
55
+ export function isRange(t) {
56
+ return t && typeof t.Type === 'object' && t.Type.Type === 'range';
57
+ }
58
+ export function isLiteralWithValue(t) {
59
+ return t && t.Type === 'literal' && 'Value' in t;
60
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "cddl",
3
- "version": "0.14.10",
3
+ "version": "0.15.0",
4
4
  "description": "Concise data definition language (RFC 8610) implementation and JSON validator in Node.js",
5
5
  "author": "Christian Bromann <mail@bromann.dev>",
6
6
  "license": "MIT",
@@ -26,6 +26,7 @@
26
26
  "@types/yargs": "^17.0.35"
27
27
  },
28
28
  "dependencies": {
29
+ "camelcase": "^9.0.0",
29
30
  "yargs": "^18.0.0"
30
31
  },
31
32
  "scripts": {
package/src/index.ts CHANGED
@@ -9,3 +9,4 @@ export function parse (filePath: string) {
9
9
  export default { parse }
10
10
  export { Lexer, Parser }
11
11
  export * from './ast.js'
12
+ export * from './utils.js'
package/src/utils.ts CHANGED
@@ -1,3 +1,15 @@
1
+ import camelcase from 'camelcase'
2
+
3
+ import type {
4
+ Assignment,
5
+ Array as CDDLArray,
6
+ Group,
7
+ NativeTypeWithOperator,
8
+ Property,
9
+ PropertyReference,
10
+ Variable
11
+ } from './ast.js'
12
+
1
13
  import { Tokens, Token } from './tokens.js'
2
14
 
3
15
  export function isLetter (ch: string): boolean {
@@ -35,3 +47,50 @@ export function parseNumberValue (token: Token): string | number {
35
47
 
36
48
  return parseInt(token.Literal, 10)
37
49
  }
50
+
51
+ export function pascalCase (name: string) {
52
+ return camelcase(name, { pascalCase: true })
53
+ }
54
+
55
+ export function isVariable (assignment: Assignment): assignment is Variable {
56
+ return assignment.Type === 'variable'
57
+ }
58
+
59
+ export function isGroup (t: any): t is Group {
60
+ return t && t.Type === 'group'
61
+ }
62
+
63
+ export function isCDDLArray (t: any): t is CDDLArray {
64
+ return t && t.Type === 'array'
65
+ }
66
+
67
+ export function isProperty (t: any): t is Property {
68
+ return t && typeof t.Name === 'string' && typeof t.HasCut === 'boolean'
69
+ }
70
+
71
+ export function isUnNamedProperty (t: any): t is Property & { Name: '' } {
72
+ return isProperty(t) && t.Name === ''
73
+ }
74
+
75
+ export function isNamedGroupReference (t: any): t is PropertyReference & { Value: string } {
76
+ return isGroup(t) && isPropertyReference(t) && typeof t.Value === 'string'
77
+ }
78
+
79
+ export function isPropertyReference (t: any): t is PropertyReference {
80
+ return t && typeof t === 'object' && 'Value' in t
81
+ }
82
+
83
+ export function isNativeTypeWithOperator (t: any): t is NativeTypeWithOperator {
84
+ return t && typeof t.Type === 'object' && 'Operator' in t
85
+ }
86
+
87
+ export function isRange (t: any): boolean {
88
+ return t && typeof t.Type === 'object' && (t.Type as any).Type === 'range'
89
+ }
90
+
91
+ export function isLiteralWithValue (t: any): t is {
92
+ Type: 'literal'
93
+ Value: unknown
94
+ } {
95
+ return t && t.Type === 'literal' && 'Value' in t
96
+ }
@@ -0,0 +1,211 @@
1
+ import { describe, it, expect } from 'vitest'
2
+
3
+ import type {
4
+ Array as CDDLArray,
5
+ Assignment,
6
+ Comment,
7
+ Group,
8
+ NativeTypeWithOperator,
9
+ Property,
10
+ PropertyReference,
11
+ Variable
12
+ } from '../src/ast.js'
13
+ import { Tokens, type Token } from '../src/tokens.js'
14
+ import {
15
+ hasSpecialNumberCharacter,
16
+ isAlphabeticCharacter,
17
+ isCDDLArray,
18
+ isDigit,
19
+ isGroup,
20
+ isLetter,
21
+ isLiteralWithValue,
22
+ isNamedGroupReference,
23
+ isNativeTypeWithOperator,
24
+ isProperty,
25
+ isPropertyReference,
26
+ isRange,
27
+ isUnNamedProperty,
28
+ isVariable,
29
+ parseNumberValue,
30
+ pascalCase
31
+ } from '../src/utils.js'
32
+
33
+ const comments: Comment[] = []
34
+
35
+ function createVariable (): Variable {
36
+ return {
37
+ Type: 'variable',
38
+ Name: 'my-variable',
39
+ IsChoiceAddition: false,
40
+ PropertyType: 'tstr',
41
+ Comments: comments
42
+ }
43
+ }
44
+
45
+ function createGroup (): Group {
46
+ return {
47
+ Type: 'group',
48
+ Name: 'my-group',
49
+ IsChoiceAddition: false,
50
+ Properties: [],
51
+ Comments: comments
52
+ }
53
+ }
54
+
55
+ function createArray (): CDDLArray {
56
+ return {
57
+ Type: 'array',
58
+ Name: 'my-array',
59
+ Values: [],
60
+ Comments: comments
61
+ }
62
+ }
63
+
64
+ function createProperty (overrides: Partial<Property> = {}): Property {
65
+ return {
66
+ HasCut: false,
67
+ Occurrence: { n: 1, m: 1 },
68
+ Name: 'foo',
69
+ Type: 'tstr',
70
+ Comments: comments,
71
+ ...overrides
72
+ }
73
+ }
74
+
75
+ describe('utils', () => {
76
+ describe('character helpers', () => {
77
+ it('should detect letters and alphabetic characters', () => {
78
+ expect(isLetter('a')).toBe(true)
79
+ expect(isLetter('Z')).toBe(true)
80
+ expect(isLetter('1')).toBe(false)
81
+
82
+ expect(isAlphabeticCharacter('a')).toBe(true)
83
+ expect(isAlphabeticCharacter(Tokens.ATSIGN)).toBe(true)
84
+ expect(isAlphabeticCharacter(Tokens.UNDERSCORE)).toBe(true)
85
+ expect(isAlphabeticCharacter(Tokens.DOLLAR)).toBe(true)
86
+ expect(isAlphabeticCharacter('-')).toBe(false)
87
+ })
88
+
89
+ it('should detect digits and special number characters', () => {
90
+ expect(isDigit('1')).toBe(true)
91
+ expect(isDigit('0')).toBe(true)
92
+ expect(isDigit('a')).toBe(false)
93
+ expect(isDigit(Tokens.NL)).toBe(false)
94
+ expect(isDigit(Tokens.SPACE)).toBe(false)
95
+
96
+ expect(hasSpecialNumberCharacter(Tokens.MINUS.charCodeAt(0))).toBe(true)
97
+ expect(hasSpecialNumberCharacter(Tokens.DOT.charCodeAt(0))).toBe(true)
98
+ expect(hasSpecialNumberCharacter('x'.charCodeAt(0))).toBe(true)
99
+ expect(hasSpecialNumberCharacter('b'.charCodeAt(0))).toBe(true)
100
+ expect(hasSpecialNumberCharacter('1'.charCodeAt(0))).toBe(false)
101
+ })
102
+ })
103
+
104
+ describe('number parsing helpers', () => {
105
+ it('should parse floats, integers and prefixed numbers', () => {
106
+ const floatToken: Token = { Type: Tokens.FLOAT, Literal: '12.5' }
107
+ const intToken: Token = { Type: Tokens.INT, Literal: '42' }
108
+ const hexToken: Token = { Type: Tokens.INT, Literal: '0x10' }
109
+ const binaryToken: Token = { Type: Tokens.INT, Literal: '0b10' }
110
+
111
+ expect(parseNumberValue(floatToken)).toBe(12.5)
112
+ expect(parseNumberValue(intToken)).toBe(42)
113
+ expect(parseNumberValue(hexToken)).toBe('0x10')
114
+ expect(parseNumberValue(binaryToken)).toBe('0b10')
115
+ })
116
+ })
117
+
118
+ describe('name helpers', () => {
119
+ it('should convert names to pascal case', () => {
120
+ expect(pascalCase('my-example_name')).toBe('MyExampleName')
121
+ })
122
+ })
123
+
124
+ describe('assignment guards', () => {
125
+ it('should detect variables, groups and arrays', () => {
126
+ const variable: Assignment = createVariable()
127
+ const group: Assignment = createGroup()
128
+ const array: Assignment = createArray()
129
+
130
+ expect(isVariable(variable)).toBe(true)
131
+ expect(isVariable(group)).toBe(false)
132
+
133
+ expect(isGroup(group)).toBe(true)
134
+ expect(isGroup(variable)).toBe(false)
135
+
136
+ expect(isCDDLArray(array)).toBe(true)
137
+ expect(isCDDLArray(group)).toBe(false)
138
+ })
139
+ })
140
+
141
+ describe('property guards', () => {
142
+ it('should detect named and unnamed properties', () => {
143
+ const property = createProperty()
144
+ const unnamedProperty = createProperty({ Name: '' })
145
+
146
+ expect(isProperty(property)).toBe(true)
147
+ expect(isProperty({ Name: 'foo' })).toBe(false)
148
+
149
+ expect(isUnNamedProperty(unnamedProperty)).toBe(true)
150
+ expect(isUnNamedProperty(property)).toBe(false)
151
+ })
152
+ })
153
+
154
+ describe('reference and operator guards', () => {
155
+ it('should detect property references and named group references', () => {
156
+ const groupReference: PropertyReference = {
157
+ Type: 'group',
158
+ Value: 'my-group',
159
+ Unwrapped: false
160
+ }
161
+ const numericGroupReference: PropertyReference = {
162
+ Type: 'group',
163
+ Value: 123,
164
+ Unwrapped: false
165
+ }
166
+
167
+ expect(isPropertyReference(groupReference)).toBe(true)
168
+ expect(isPropertyReference({ Type: 'group' })).toBe(false)
169
+
170
+ expect(isNamedGroupReference(groupReference)).toBe(true)
171
+ expect(isNamedGroupReference(numericGroupReference)).toBe(false)
172
+ })
173
+
174
+ it('should detect native types with operators and ranges', () => {
175
+ const nativeTypeWithOperator: NativeTypeWithOperator = {
176
+ Type: {
177
+ Type: 'group',
178
+ Value: 'my-group',
179
+ Unwrapped: false
180
+ },
181
+ Operator: {
182
+ Type: 'default',
183
+ Value: 'tstr'
184
+ }
185
+ }
186
+ const rangeReference: PropertyReference = {
187
+ Type: 'range',
188
+ Value: {
189
+ Min: 0,
190
+ Max: 10,
191
+ Inclusive: true
192
+ },
193
+ Unwrapped: false
194
+ }
195
+
196
+ expect(isNativeTypeWithOperator(nativeTypeWithOperator)).toBe(true)
197
+ expect(isNativeTypeWithOperator({ Type: 'tstr' })).toBe(false)
198
+
199
+ expect(isRange({ Type: rangeReference })).toBe(true)
200
+ expect(isRange({ Type: 'range' })).toBe(false)
201
+ })
202
+ })
203
+
204
+ describe('literal guards', () => {
205
+ it('should detect literals with values', () => {
206
+ expect(isLiteralWithValue({ Type: 'literal', Value: 'foo' })).toBe(true)
207
+ expect(isLiteralWithValue({ Type: 'literal' })).toBe(false)
208
+ expect(isLiteralWithValue({ Type: 'group', Value: 'foo' })).toBe(false)
209
+ })
210
+ })
211
+ })