cddl2py 0.0.1 → 0.1.1

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.
@@ -1,92 +0,0 @@
1
- import url from 'node:url'
2
- import path from 'node:path'
3
- import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest'
4
-
5
- import cli from '../src/cli.js'
6
-
7
- const __dirname = url.fileURLToPath(new URL('.', import.meta.url))
8
- const cddlFile = path.join(__dirname, '..', '..', '..', 'examples', 'commons', 'complex_types.cddl')
9
-
10
- vi.mock('../src/constants', () => ({
11
- pkg: {
12
- name: 'cddl2py',
13
- version: '0.1.0',
14
- author: 'Test Author',
15
- description: 'Generate Python types from CDDL'
16
- },
17
- NATIVE_TYPE_MAP: {
18
- any: 'Any',
19
- number: 'Union[int, float]',
20
- int: 'int',
21
- uint: 'int',
22
- nint: 'int',
23
- float: 'float',
24
- float16: 'float',
25
- float32: 'float',
26
- float64: 'float',
27
- bool: 'bool',
28
- bstr: 'bytes',
29
- bytes: 'bytes',
30
- tstr: 'str',
31
- text: 'str',
32
- str: 'str',
33
- nil: 'None',
34
- null: 'None',
35
- }
36
- }))
37
-
38
- describe('complex types conversion', () => {
39
- let exitOrig = process.exit
40
- let logOrig = console.log
41
- let errorOrig = console.error
42
-
43
- beforeEach(() => {
44
- process.exit = vi.fn() as any
45
- console.log = vi.fn()
46
- console.error = vi.fn()
47
- })
48
-
49
- afterEach(() => {
50
- process.exit = exitOrig
51
- console.log = logOrig
52
- console.error = errorOrig
53
- })
54
-
55
- it('should include all types in the union (TypedDict)', async () => {
56
- await cli([cddlFile])
57
-
58
- expect(process.exit).not.toHaveBeenCalledWith(1)
59
- expect(console.error).not.toHaveBeenCalled()
60
- expect(console.log).toHaveBeenCalled()
61
- const output = vi.mocked(console.log).mock.calls.flat().join('\n')
62
-
63
- expect(output).toContain('ArrayLocalValue')
64
- expect(output).toContain('DateLocalValue')
65
- expect(output).toContain('MapLocalValue')
66
- expect(output).toContain('ObjectLocalValue')
67
- expect(output).toContain('RegExpLocalValue')
68
- expect(output).toContain('SetLocalValue')
69
-
70
- expect(output).toContain('LocalValue = Union[ArrayLocalValue, DateLocalValue, MapLocalValue, ObjectLocalValue, RegExpLocalValue, SetLocalValue]')
71
- expect(output).toMatchSnapshot()
72
- })
73
-
74
- it('should include all types in the union (Pydantic)', async () => {
75
- await cli([cddlFile, '--pydantic'])
76
-
77
- expect(process.exit).not.toHaveBeenCalledWith(1)
78
- expect(console.error).not.toHaveBeenCalled()
79
- expect(console.log).toHaveBeenCalled()
80
- const output = vi.mocked(console.log).mock.calls.flat().join('\n')
81
-
82
- expect(output).toContain('ArrayLocalValue')
83
- expect(output).toContain('DateLocalValue')
84
- expect(output).toContain('MapLocalValue')
85
- expect(output).toContain('ObjectLocalValue')
86
- expect(output).toContain('RegExpLocalValue')
87
- expect(output).toContain('SetLocalValue')
88
-
89
- expect(output).toContain('LocalValue = Union[ArrayLocalValue, DateLocalValue, MapLocalValue, ObjectLocalValue, RegExpLocalValue, SetLocalValue]')
90
- expect(output).toMatchSnapshot()
91
- })
92
- })
@@ -1,88 +0,0 @@
1
- import url from 'node:url'
2
- import path from 'node:path'
3
- import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest'
4
-
5
- import cli from '../src/cli.js'
6
-
7
- const __dirname = url.fileURLToPath(new URL('.', import.meta.url))
8
- const groupChoiceCDDL = path.join(__dirname, '..', '..', '..', 'examples', 'commons', 'group_choice.cddl')
9
-
10
- vi.mock('../src/constants', () => ({
11
- pkg: {
12
- name: 'cddl2py',
13
- version: '0.1.0',
14
- author: 'Test Author',
15
- description: 'Generate Python types from CDDL'
16
- },
17
- NATIVE_TYPE_MAP: {
18
- any: 'Any',
19
- number: 'Union[int, float]',
20
- int: 'int',
21
- uint: 'int',
22
- nint: 'int',
23
- float: 'float',
24
- float16: 'float',
25
- float32: 'float',
26
- float64: 'float',
27
- bool: 'bool',
28
- bstr: 'bytes',
29
- bytes: 'bytes',
30
- tstr: 'str',
31
- text: 'str',
32
- str: 'str',
33
- nil: 'None',
34
- null: 'None',
35
- }
36
- }))
37
-
38
- describe('group choice conversion', () => {
39
- let exitOrig = process.exit
40
- let logOrig = console.log
41
- let errorOrig = console.error
42
-
43
- beforeEach(() => {
44
- process.exit = vi.fn() as any
45
- console.log = vi.fn()
46
- console.error = vi.fn()
47
- })
48
-
49
- afterEach(() => {
50
- process.exit = exitOrig
51
- console.log = logOrig
52
- console.error = errorOrig
53
- })
54
-
55
- it('should generate a union type for multiple group choices (TypedDict)', async () => {
56
- await cli([groupChoiceCDDL])
57
-
58
- expect(process.exit).not.toHaveBeenCalledWith(1)
59
- expect(console.error).not.toHaveBeenCalled()
60
- expect(console.log).toHaveBeenCalled()
61
- const output = vi.mocked(console.log).mock.calls.flat().join('\n')
62
-
63
- expect(output).toContain('ProxyConfiguration = Union[AutodetectProxyConfiguration, DirectProxyConfiguration, ManualProxyConfiguration]')
64
-
65
- expect(output).toContain('class AutodetectProxyConfiguration(Extensible):')
66
- expect(output).toContain('class DirectProxyConfiguration(Extensible):')
67
- expect(output).toContain('class ManualProxyConfiguration(Extensible):')
68
-
69
- expect(output).toMatchSnapshot()
70
- })
71
-
72
- it('should generate a union type for multiple group choices (Pydantic)', async () => {
73
- await cli([groupChoiceCDDL, '--pydantic'])
74
-
75
- expect(process.exit).not.toHaveBeenCalledWith(1)
76
- expect(console.error).not.toHaveBeenCalled()
77
- expect(console.log).toHaveBeenCalled()
78
- const output = vi.mocked(console.log).mock.calls.flat().join('\n')
79
-
80
- expect(output).toContain('ProxyConfiguration = Union[AutodetectProxyConfiguration, DirectProxyConfiguration, ManualProxyConfiguration]')
81
-
82
- expect(output).toContain('class AutodetectProxyConfiguration(Extensible):')
83
- expect(output).toContain('class DirectProxyConfiguration(Extensible):')
84
- expect(output).toContain('class ManualProxyConfiguration(Extensible):')
85
-
86
- expect(output).toMatchSnapshot()
87
- })
88
- })
@@ -1,63 +0,0 @@
1
- import url from 'node:url'
2
- import path from 'node:path'
3
- import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest'
4
-
5
- import cli from '../src/cli.js'
6
-
7
- const __dirname = url.fileURLToPath(new URL('.', import.meta.url))
8
- const cddlFile = path.join(__dirname, '..', '..', '..', 'examples', 'commons', 'literals.cddl')
9
-
10
- vi.mock('../src/constants', () => ({
11
- pkg: {
12
- name: 'cddl2py',
13
- version: '0.1.0',
14
- author: 'Test Author',
15
- description: 'Generate Python types from CDDL'
16
- },
17
- NATIVE_TYPE_MAP: {
18
- any: 'Any',
19
- number: 'Union[int, float]',
20
- int: 'int',
21
- uint: 'int',
22
- nint: 'int',
23
- float: 'float',
24
- float16: 'float',
25
- float32: 'float',
26
- float64: 'float',
27
- bool: 'bool',
28
- bstr: 'bytes',
29
- bytes: 'bytes',
30
- tstr: 'str',
31
- text: 'str',
32
- str: 'str',
33
- nil: 'None',
34
- null: 'None',
35
- }
36
- }))
37
-
38
- describe('literals', () => {
39
- let exitOrig = process.exit
40
- let logOrig = console.log
41
- let errorOrig = console.error
42
-
43
- beforeEach(() => {
44
- process.exit = vi.fn() as any
45
- console.log = vi.fn()
46
- console.error = vi.fn()
47
- })
48
-
49
- afterEach(() => {
50
- process.exit = exitOrig
51
- console.log = logOrig
52
- console.error = errorOrig
53
- })
54
-
55
- it('should support bigint and null literals', async () => {
56
- await cli([cddlFile])
57
-
58
- expect(process.exit).not.toHaveBeenCalledWith(1)
59
- expect(console.error).not.toHaveBeenCalled()
60
- const output = vi.mocked(console.log).mock.calls.flat().join('\n')
61
- expect(output).toMatchSnapshot()
62
- })
63
- })
@@ -1,80 +0,0 @@
1
- import url from 'node:url'
2
- import path from 'node:path'
3
- import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest'
4
-
5
- import cli from '../src/cli.js'
6
-
7
- const __dirname = url.fileURLToPath(new URL('.', import.meta.url))
8
- const cddlFile = path.join(__dirname, '..', '..', '..', 'examples', 'commons', 'mixin_union.cddl')
9
-
10
- vi.mock('../src/constants', () => ({
11
- pkg: {
12
- name: 'cddl2py',
13
- version: '0.1.0',
14
- author: 'Test Author',
15
- description: 'Generate Python types from CDDL'
16
- },
17
- NATIVE_TYPE_MAP: {
18
- any: 'Any',
19
- number: 'Union[int, float]',
20
- int: 'int',
21
- uint: 'int',
22
- nint: 'int',
23
- float: 'float',
24
- float16: 'float',
25
- float32: 'float',
26
- float64: 'float',
27
- bool: 'bool',
28
- bstr: 'bytes',
29
- bytes: 'bytes',
30
- tstr: 'str',
31
- text: 'str',
32
- str: 'str',
33
- nil: 'None',
34
- null: 'None',
35
- }
36
- }))
37
-
38
- describe('mixin and union conversion', () => {
39
- let exitOrig = process.exit
40
- let logOrig = console.log
41
- let errorOrig = console.error
42
-
43
- beforeEach(() => {
44
- process.exit = vi.fn() as any
45
- console.log = vi.fn()
46
- console.error = vi.fn()
47
- })
48
-
49
- afterEach(() => {
50
- process.exit = exitOrig
51
- console.log = logOrig
52
- console.error = errorOrig
53
- })
54
-
55
- it('should generate union type aliases for mixin choices (TypedDict)', async () => {
56
- await cli([cddlFile])
57
-
58
- expect(process.exit).not.toHaveBeenCalledWith(1)
59
- expect(console.error).not.toHaveBeenCalled()
60
-
61
- const output = vi.mocked(console.log).mock.calls.flat().join('\n')
62
-
63
- expect(output).toContain('class Mixins(MixinA, MixinB):')
64
- expect(output).toContain('UnionMixin = Union[MixinA, MixinB]')
65
- expect(output).toMatchSnapshot()
66
- })
67
-
68
- it('should generate union type aliases for mixin choices (Pydantic)', async () => {
69
- await cli([cddlFile, '--pydantic'])
70
-
71
- expect(process.exit).not.toHaveBeenCalledWith(1)
72
- expect(console.error).not.toHaveBeenCalled()
73
-
74
- const output = vi.mocked(console.log).mock.calls.flat().join('\n')
75
-
76
- expect(output).toContain('class Mixins(MixinA, MixinB):')
77
- expect(output).toContain('UnionMixin = Union[MixinA, MixinB]')
78
- expect(output).toMatchSnapshot()
79
- })
80
- })
package/tests/mod.test.ts DELETED
@@ -1,106 +0,0 @@
1
- import url from 'node:url'
2
- import path from 'node:path'
3
- import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest'
4
-
5
- import cli from '../src/cli.js'
6
-
7
- const __dirname = url.fileURLToPath(new URL('.', import.meta.url))
8
-
9
- vi.mock('../src/constants', () => ({
10
- pkg: {
11
- name: 'cddl2py',
12
- version: '0.1.0',
13
- author: 'Test Author',
14
- description: 'Generate Python types from CDDL'
15
- },
16
- NATIVE_TYPE_MAP: {
17
- any: 'Any',
18
- number: 'Union[int, float]',
19
- int: 'int',
20
- uint: 'int',
21
- nint: 'int',
22
- float: 'float',
23
- float16: 'float',
24
- float32: 'float',
25
- float64: 'float',
26
- bool: 'bool',
27
- bstr: 'bytes',
28
- bytes: 'bytes',
29
- tstr: 'str',
30
- text: 'str',
31
- str: 'str',
32
- nil: 'None',
33
- null: 'None',
34
- }
35
- }))
36
-
37
- describe('cddl2py CLI', () => {
38
- const exitOrig = process.exit.bind(process)
39
- const logOrig = console.log.bind(console)
40
- const errorOrig = console.error.bind(console)
41
-
42
- beforeEach(() => {
43
- // @ts-expect-error
44
- process.exit = vi.fn(() => {})
45
- console.log = vi.fn()
46
- console.error = vi.fn()
47
- })
48
-
49
- it('should print help if no args were provided', async () => {
50
- await cli([])
51
-
52
- expect(console.error).toHaveBeenCalledWith(expect.stringMatching(/cddl2py/))
53
- expect(process.exit).toHaveBeenCalledWith(0)
54
- })
55
-
56
- it('should print help when --help is set', async () => {
57
- await cli(['foo', 'bar', '--help', 'barfoo'])
58
-
59
- expect(console.log).toHaveBeenCalledWith(expect.stringMatching(/cddl2py/))
60
- expect(process.exit).toHaveBeenCalledWith(0)
61
- })
62
-
63
- it('should print version (alias)', async () => {
64
- await cli(['foo', '-v', 'bar'])
65
-
66
- expect(console.log).toHaveBeenCalledWith('0.1.0')
67
- expect(process.exit).toHaveBeenCalledWith(0)
68
- })
69
-
70
- it('should print version (long flag)', async () => {
71
- await cli(['foo', '--version', 'bar'])
72
-
73
- expect(console.log).toHaveBeenCalledWith('0.1.0')
74
- expect(process.exit).toHaveBeenCalledWith(0)
75
- })
76
-
77
- it('should fail if first parameter is not pointing to a file', async () => {
78
- await cli(['nonexistent.cddl'])
79
-
80
- expect(console.error).toHaveBeenCalledTimes(1)
81
- expect(process.exit).toHaveBeenCalledWith(1)
82
- })
83
-
84
- it('should generate correct types for test.cddl', async () => {
85
- await cli([path.join(__dirname, '..', '..', '..', 'examples', 'commons', 'test.cddl')])
86
-
87
- expect(vi.mocked(console.log).mock.calls).toMatchSnapshot()
88
- expect(process.exit).toHaveBeenCalledTimes(0)
89
- })
90
-
91
- it('should generate correct pydantic types for test.cddl', async () => {
92
- await cli([
93
- path.join(__dirname, '..', '..', '..', 'examples', 'commons', 'test.cddl'),
94
- '--pydantic'
95
- ])
96
-
97
- expect(vi.mocked(console.log).mock.calls).toMatchSnapshot()
98
- expect(process.exit).toHaveBeenCalledTimes(0)
99
- })
100
-
101
- afterEach(() => {
102
- process.exit = exitOrig
103
- console.log = logOrig
104
- console.error = errorOrig
105
- })
106
- })
@@ -1,82 +0,0 @@
1
- import url from 'node:url'
2
- import path from 'node:path'
3
- import { describe, it, expect, vi, beforeEach, afterEach } from 'vitest'
4
-
5
- import cli from '../src/cli.js'
6
-
7
- const __dirname = url.fileURLToPath(new URL('.', import.meta.url))
8
- const cddlFile = path.join(__dirname, '..', '..', '..', 'examples', 'commons', 'named_group_choice.cddl')
9
-
10
- vi.mock('../src/constants', () => ({
11
- pkg: {
12
- name: 'cddl2py',
13
- version: '0.1.0',
14
- author: 'Test Author',
15
- description: 'Generate Python types from CDDL'
16
- },
17
- NATIVE_TYPE_MAP: {
18
- any: 'Any',
19
- number: 'Union[int, float]',
20
- int: 'int',
21
- uint: 'int',
22
- nint: 'int',
23
- float: 'float',
24
- float16: 'float',
25
- float32: 'float',
26
- float64: 'float',
27
- bool: 'bool',
28
- bstr: 'bytes',
29
- bytes: 'bytes',
30
- tstr: 'str',
31
- text: 'str',
32
- str: 'str',
33
- nil: 'None',
34
- null: 'None',
35
- }
36
- }))
37
-
38
- describe('named group choice', () => {
39
- let exitOrig = process.exit
40
- let logOrig = console.log
41
- let errorOrig = console.error
42
-
43
- beforeEach(() => {
44
- process.exit = vi.fn() as any
45
- console.log = vi.fn()
46
- console.error = vi.fn()
47
- })
48
-
49
- afterEach(() => {
50
- process.exit = exitOrig
51
- console.log = logOrig
52
- console.error = errorOrig
53
- })
54
-
55
- it('should generate a union type alias for named group references (TypedDict)', async () => {
56
- await cli([cddlFile])
57
-
58
- expect(process.exit).not.toHaveBeenCalledWith(1)
59
- expect(console.error).not.toHaveBeenCalled()
60
-
61
- const output = vi.mocked(console.log).mock.calls.flat().join('\n')
62
-
63
- expect(output).toContain('Choice = Union[OptionA, OptionB]')
64
- expect(output).toContain('class OptionA(TypedDict):')
65
- expect(output).toContain('class OptionB(TypedDict):')
66
- expect(output).toMatchSnapshot()
67
- })
68
-
69
- it('should generate a union type alias for named group references (Pydantic)', async () => {
70
- await cli([cddlFile, '--pydantic'])
71
-
72
- expect(process.exit).not.toHaveBeenCalledWith(1)
73
- expect(console.error).not.toHaveBeenCalled()
74
-
75
- const output = vi.mocked(console.log).mock.calls.flat().join('\n')
76
-
77
- expect(output).toContain('Choice = Union[OptionA, OptionB]')
78
- expect(output).toContain('class OptionA(BaseModel):')
79
- expect(output).toContain('class OptionB(BaseModel):')
80
- expect(output).toMatchSnapshot()
81
- })
82
- })
@@ -1,149 +0,0 @@
1
- import url from 'node:url'
2
- import path from 'node:path'
3
- import { describe, it, expect } from 'vitest'
4
- import { parse } from 'cddl'
5
- import { transform } from '../src/index.js'
6
- import type { Variable, Group, Array as CDDLArray } from 'cddl'
7
-
8
- const __dirname = url.fileURLToPath(new URL('.', import.meta.url))
9
-
10
- describe('transform', () => {
11
- describe('variables', () => {
12
- it('should transform a simple variable assignment', () => {
13
- const assignment: Variable = {
14
- Type: 'variable',
15
- Name: 'device-address',
16
- PropertyType: 'tstr',
17
- Comments: [],
18
- IsChoiceAddition: false
19
- }
20
- const output = transform([assignment])
21
- expect(output).toContain('DeviceAddress = str')
22
- })
23
-
24
- it('should transform union variable', () => {
25
- const assignment: Variable = {
26
- Type: 'variable',
27
- Name: 'my-type',
28
- PropertyType: ['int', 'tstr'],
29
- Comments: [],
30
- IsChoiceAddition: false
31
- }
32
- const output = transform([assignment])
33
- expect(output).toContain('MyType = Union[int, str]')
34
- })
35
-
36
- it('should transform bigint literals', () => {
37
- const assignment: Variable = {
38
- Type: 'variable',
39
- Name: 'MyBigInt',
40
- PropertyType: {
41
- Type: 'literal',
42
- Value: 9007199254740995n
43
- } as any,
44
- Comments: [],
45
- IsChoiceAddition: false
46
- }
47
- const output = transform([assignment])
48
- expect(output).toContain('MyBigInt = Literal[9007199254740995]')
49
- })
50
- })
51
-
52
- describe('groups (TypedDict)', () => {
53
- it('should transform a simple group into a TypedDict', () => {
54
- const assignment: Group = {
55
- Type: 'group',
56
- Name: 'person',
57
- IsChoiceAddition: false,
58
- Properties: [
59
- { HasCut: false, Occurrence: { n: 1, m: 1 }, Name: 'age', Type: 'int', Comments: [] },
60
- { HasCut: false, Occurrence: { n: 1, m: 1 }, Name: 'name', Type: 'tstr', Comments: [] }
61
- ] as any,
62
- Comments: []
63
- }
64
- const output = transform([assignment])
65
- expect(output).toContain('class Person(TypedDict):')
66
- expect(output).toContain(' age: int')
67
- expect(output).toContain(' name: str')
68
- })
69
-
70
- it('should handle optional fields with NotRequired', () => {
71
- const assignment: Group = {
72
- Type: 'group',
73
- Name: 'person',
74
- IsChoiceAddition: false,
75
- Properties: [
76
- { HasCut: false, Occurrence: { n: 0, m: 1 }, Name: 'nickname', Type: 'tstr', Comments: [] },
77
- ] as any,
78
- Comments: []
79
- }
80
- const output = transform([assignment])
81
- expect(output).toContain('class Person(TypedDict):')
82
- expect(output).toContain(' nickname: NotRequired[str]')
83
- })
84
- })
85
-
86
- describe('groups (Pydantic)', () => {
87
- it('should transform a simple group into a Pydantic BaseModel', () => {
88
- const assignment: Group = {
89
- Type: 'group',
90
- Name: 'person',
91
- IsChoiceAddition: false,
92
- Properties: [
93
- { HasCut: false, Occurrence: { n: 1, m: 1 }, Name: 'age', Type: 'int', Comments: [] },
94
- { HasCut: false, Occurrence: { n: 1, m: 1 }, Name: 'name', Type: 'tstr', Comments: [] }
95
- ] as any,
96
- Comments: []
97
- }
98
- const output = transform([assignment], { pydantic: true })
99
- expect(output).toContain('from pydantic import BaseModel')
100
- expect(output).toContain('class Person(BaseModel):')
101
- expect(output).toContain(' age: int')
102
- expect(output).toContain(' name: str')
103
- })
104
-
105
- it('should handle optional fields with Optional and None default', () => {
106
- const assignment: Group = {
107
- Type: 'group',
108
- Name: 'person',
109
- IsChoiceAddition: false,
110
- Properties: [
111
- { HasCut: false, Occurrence: { n: 0, m: 1 }, Name: 'nickname', Type: 'tstr', Comments: [] },
112
- ] as any,
113
- Comments: []
114
- }
115
- const output = transform([assignment], { pydantic: true })
116
- expect(output).toContain('class Person(BaseModel):')
117
- expect(output).toContain(' nickname: Optional[str] = None')
118
- })
119
- })
120
-
121
- describe('arrays', () => {
122
- it('should transform an array definition', () => {
123
- const assignment: CDDLArray = {
124
- Type: 'array',
125
- Name: 'my-list',
126
- Values: [
127
- { HasCut: false, Occurrence: { n: 0, m: Infinity }, Name: '', Type: 'int', Comments: [] }
128
- ] as any,
129
- Comments: []
130
- }
131
- const output = transform([assignment])
132
- expect(output).toContain('MyList = list[int]')
133
- })
134
- })
135
-
136
- describe('snapshot tests with parsed CDDL', () => {
137
- it('should transform test.cddl TypedDict correctly', () => {
138
- const ast = parse(path.join(__dirname, '..', '..', '..', 'examples', 'commons', 'test.cddl'))
139
- const output = transform(ast)
140
- expect(output).toMatchSnapshot()
141
- })
142
-
143
- it('should transform test.cddl Pydantic correctly', () => {
144
- const ast = parse(path.join(__dirname, '..', '..', '..', 'examples', 'commons', 'test.cddl'))
145
- const output = transform(ast, { pydantic: true })
146
- expect(output).toMatchSnapshot()
147
- })
148
- })
149
- })