Skip to content

Commit 35bda10

Browse files
author
Ferdi Koomen
committed
- Fixed binary format checking
1 parent 9c9b2fa commit 35bda10

File tree

11 files changed

+65
-89
lines changed

11 files changed

+65
-89
lines changed

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "openapi-typescript-codegen",
3-
"version": "0.11.7",
3+
"version": "0.11.8",
44
"description": "Library that generates Typescript clients based on the OpenAPI specification.",
55
"author": "Ferdi Koomen",
66
"homepage": "https://github.com/ferdikoomen/openapi-typescript-codegen",

src/openApi/v2/parser/getMappedType.ts

Lines changed: 5 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
export const TYPE_MAPPINGS = new Map<string, string>([
1+
const TYPE_MAPPINGS = new Map<string, string>([
22
['File', 'File'],
33
['file', 'File'],
44
['any', 'any'],
@@ -25,10 +25,9 @@ export const TYPE_MAPPINGS = new Map<string, string>([
2525
/**
2626
* Get mapped type for given type to any basic Typescript/Javascript type.
2727
*/
28-
export function getMappedType(type: string): string | undefined {
28+
export function getMappedType(type: string, format?: string): string | undefined {
29+
if (format === 'binary') {
30+
return 'File';
31+
}
2932
return TYPE_MAPPINGS.get(type);
3033
}
31-
32-
export function hasMappedType(type: string): boolean {
33-
return TYPE_MAPPINGS.has(type);
34-
}

src/openApi/v2/parser/getModel.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -153,7 +153,7 @@ export function getModel(
153153

154154
// If the schema has a type than it can be a basic or generic type.
155155
if (definition.type) {
156-
const definitionType = getType(definition.type);
156+
const definitionType = getType(definition.type, definition.format);
157157
model.export = 'generic';
158158
model.type = definitionType.type;
159159
model.base = definitionType.base;

src/openApi/v2/parser/getOperationParameter.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -84,7 +84,7 @@ export function getOperationParameter(openApi: OpenApi, parameter: OpenApiParame
8484
}
8585

8686
if (parameter.type === 'array' && parameter.items) {
87-
const items = getType(parameter.items.type);
87+
const items = getType(parameter.items.type, parameter.items.format);
8888
operationParameter.export = 'array';
8989
operationParameter.type = items.type;
9090
operationParameter.base = items.base;
@@ -95,7 +95,7 @@ export function getOperationParameter(openApi: OpenApi, parameter: OpenApiParame
9595
}
9696

9797
if (parameter.type === 'object' && parameter.items) {
98-
const items = getType(parameter.items.type);
98+
const items = getType(parameter.items.type, parameter.items.format);
9999
operationParameter.export = 'dictionary';
100100
operationParameter.type = items.type;
101101
operationParameter.base = items.base;
@@ -137,7 +137,7 @@ export function getOperationParameter(openApi: OpenApi, parameter: OpenApiParame
137137

138138
// If the parameter has a type than it can be a basic or generic type.
139139
if (parameter.type) {
140-
const definitionType = getType(parameter.type);
140+
const definitionType = getType(parameter.type, parameter.format);
141141
operationParameter.export = 'generic';
142142
operationParameter.type = definitionType.type;
143143
operationParameter.base = definitionType.base;

src/openApi/v2/parser/getType.spec.ts

Lines changed: 0 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -49,14 +49,6 @@ describe('getType', () => {
4949
expect(type.imports).toEqual(['Link', 'Link']);
5050
});
5151

52-
it('should convert generic', () => {
53-
const type = getType('#/definitions/Link', 'Link');
54-
expect(type.type).toEqual('T');
55-
expect(type.base).toEqual('T');
56-
expect(type.template).toEqual(null);
57-
expect(type.imports).toEqual([]);
58-
});
59-
6052
it('should support dot', () => {
6153
const type = getType('#/definitions/model.000');
6254
expect(type.type).toEqual('model_000');

src/openApi/v2/parser/getType.ts

Lines changed: 20 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,5 @@
11
import type { Type } from '../../../client/interfaces/Type';
2-
import { getMappedType, hasMappedType } from './getMappedType';
2+
import { getMappedType } from './getMappedType';
33
import { stripNamespace } from './stripNamespace';
44

55
function encode(value: string): string {
@@ -8,10 +8,10 @@ function encode(value: string): string {
88

99
/**
1010
* Parse any string value into a type object.
11-
* @param value String value like "integer" or "Link[Model]".
12-
* @param template Optional template class from parent (needed to process generics)
11+
* @param type String value like "integer" or "Link[Model]".
12+
* @param format String value like "binary" or "date".
1313
*/
14-
export function getType(value?: string, template?: string): Type {
14+
export function getType(type: string = 'any', format?: string): Type {
1515
const result: Type = {
1616
type: 'any',
1717
base: 'any',
@@ -20,10 +20,17 @@ export function getType(value?: string, template?: string): Type {
2020
isNullable: false,
2121
};
2222

23-
const valueClean = decodeURIComponent(stripNamespace(value || ''));
23+
const mapped = getMappedType(type, format);
24+
if (mapped) {
25+
result.type = mapped;
26+
result.base = mapped;
27+
return result;
28+
}
29+
30+
const typeWithoutNamespace = decodeURIComponent(stripNamespace(type));
2431

25-
if (/\[.*\]$/g.test(valueClean)) {
26-
const matches = valueClean.match(/(.*?)\[(.*)\]$/);
32+
if (/\[.*\]$/g.test(typeWithoutNamespace)) {
33+
const matches = typeWithoutNamespace.match(/(.*?)\[(.*)\]$/);
2734
if (matches?.length) {
2835
const match1 = getType(encode(matches[1]));
2936
const match2 = getType(encode(matches[2]));
@@ -44,26 +51,16 @@ export function getType(value?: string, template?: string): Type {
4451

4552
result.imports.push(...match1.imports);
4653
result.imports.push(...match2.imports);
54+
return result;
4755
}
48-
} else if (hasMappedType(valueClean)) {
49-
const mapped = getMappedType(valueClean);
50-
if (mapped) {
51-
result.type = mapped;
52-
result.base = mapped;
53-
}
54-
} else if (valueClean) {
55-
const type = encode(valueClean);
56+
}
57+
58+
if (typeWithoutNamespace) {
59+
const type = encode(typeWithoutNamespace);
5660
result.type = type;
5761
result.base = type;
5862
result.imports.push(type);
59-
}
60-
61-
// If the property that we found matched the parent template class
62-
// Then ignore this whole property and return it as a "T" template property.
63-
if (result.type === template) {
64-
result.type = 'T'; // Template;
65-
result.base = 'T'; // Template;
66-
result.imports = [];
63+
return result;
6764
}
6865

6966
return result;

src/openApi/v3/parser/getMappedType.ts

Lines changed: 5 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
export const TYPE_MAPPINGS = new Map<string, string>([
1+
const TYPE_MAPPINGS = new Map<string, string>([
22
['File', 'File'],
33
['file', 'File'],
44
['any', 'any'],
@@ -25,10 +25,9 @@ export const TYPE_MAPPINGS = new Map<string, string>([
2525
/**
2626
* Get mapped type for given type to any basic Typescript/Javascript type.
2727
*/
28-
export function getMappedType(type: string): string | undefined {
28+
export function getMappedType(type: string, format?: string): string | undefined {
29+
if (format === 'binary') {
30+
return 'File';
31+
}
2932
return TYPE_MAPPINGS.get(type);
3033
}
31-
32-
export function hasMappedType(type: string): boolean {
33-
return TYPE_MAPPINGS.has(type);
34-
}

src/openApi/v3/parser/getModel.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -180,7 +180,7 @@ export function getModel(
180180

181181
// If the schema has a type than it can be a basic or generic type.
182182
if (definition.type) {
183-
const definitionType = getType(definition.type);
183+
const definitionType = getType(definition.type, definition.format);
184184
model.export = 'generic';
185185
model.type = definitionType.type;
186186
model.base = definitionType.base;

src/openApi/v3/parser/getType.spec.ts

Lines changed: 0 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -55,15 +55,6 @@ describe('getType', () => {
5555
expect(type.isNullable).toEqual(false);
5656
});
5757

58-
it('should convert generic', () => {
59-
const type = getType('#/components/schemas/Link', 'Link');
60-
expect(type.type).toEqual('T');
61-
expect(type.base).toEqual('T');
62-
expect(type.template).toEqual(null);
63-
expect(type.imports).toEqual([]);
64-
expect(type.isNullable).toEqual(false);
65-
});
66-
6758
it('should support dot', () => {
6859
const type = getType('#/components/schemas/model.000');
6960
expect(type.type).toEqual('model_000');

src/openApi/v3/parser/getType.ts

Lines changed: 28 additions & 30 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
import type { Type } from '../../../client/interfaces/Type';
2-
import { getMappedType, hasMappedType } from './getMappedType';
2+
import { isDefined } from '../../../utils/isDefined';
3+
import { getMappedType } from './getMappedType';
34
import { stripNamespace } from './stripNamespace';
45

56
function encode(value: string): string {
@@ -8,10 +9,10 @@ function encode(value: string): string {
89

910
/**
1011
* Parse any string value into a type object.
11-
* @param values String or String[] value like "integer", "Link[Model]" or ["string", "null"]
12-
* @param template Optional template class from parent (needed to process generics)
12+
* @param type String or String[] value like "integer", "Link[Model]" or ["string", "null"].
13+
* @param format String value like "binary" or "date".
1314
*/
14-
export function getType(values?: string | string[], template?: string): Type {
15+
export function getType(type: string | string[] = 'any', format?: string): Type {
1516
const result: Type = {
1617
type: 'any',
1718
base: 'any',
@@ -22,22 +23,29 @@ export function getType(values?: string | string[], template?: string): Type {
2223

2324
// Special case for JSON Schema spec (december 2020, page 17),
2425
// that allows type to be an array of primitive types...
25-
if (Array.isArray(values)) {
26-
const type = values
26+
if (Array.isArray(type)) {
27+
const joinedType = type
2728
.filter(value => value !== 'null')
28-
.filter(value => hasMappedType(value))
29-
.map(value => getMappedType(value))
29+
.map(value => getMappedType(value, format))
30+
.filter(isDefined)
3031
.join(' | ');
31-
result.type = type;
32-
result.base = type;
33-
result.isNullable = values.includes('null');
32+
result.type = joinedType;
33+
result.base = joinedType;
34+
result.isNullable = type.includes('null');
35+
return result;
36+
}
37+
38+
const mapped = getMappedType(type, format);
39+
if (mapped) {
40+
result.type = mapped;
41+
result.base = mapped;
3442
return result;
3543
}
3644

37-
const valueClean = decodeURIComponent(stripNamespace(values || ''));
45+
const typeWithoutNamespace = decodeURIComponent(stripNamespace(type));
3846

39-
if (/\[.*\]$/g.test(valueClean)) {
40-
const matches = valueClean.match(/(.*?)\[(.*)\]$/);
47+
if (/\[.*\]$/g.test(typeWithoutNamespace)) {
48+
const matches = typeWithoutNamespace.match(/(.*?)\[(.*)\]$/);
4149
if (matches?.length) {
4250
const match1 = getType(encode(matches[1]));
4351
const match2 = getType(encode(matches[2]));
@@ -58,26 +66,16 @@ export function getType(values?: string | string[], template?: string): Type {
5866

5967
result.imports.push(...match1.imports);
6068
result.imports.push(...match2.imports);
69+
return result;
6170
}
62-
} else if (hasMappedType(valueClean)) {
63-
const mapped = getMappedType(valueClean);
64-
if (mapped) {
65-
result.type = mapped;
66-
result.base = mapped;
67-
}
68-
} else if (valueClean) {
69-
const type = encode(valueClean);
71+
}
72+
73+
if (typeWithoutNamespace) {
74+
const type = encode(typeWithoutNamespace);
7075
result.type = type;
7176
result.base = type;
7277
result.imports.push(type);
73-
}
74-
75-
// If the property that we found matched the parent template class
76-
// Then ignore this whole property and return it as a "T" template property.
77-
if (result.type === template) {
78-
result.type = 'T'; // Template;
79-
result.base = 'T'; // Template;
80-
result.imports = [];
78+
return result;
8179
}
8280

8381
return result;

0 commit comments

Comments
 (0)