Skip to content

Commit

Permalink
wip, change openapi types naming, simplify code
Browse files Browse the repository at this point in the history
  • Loading branch information
kainpets committed Jul 9, 2024
1 parent cfd50d0 commit 78ec7d3
Show file tree
Hide file tree
Showing 4 changed files with 78 additions and 84 deletions.
77 changes: 38 additions & 39 deletions src/lib/blueprint.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,10 @@
import type {
OpenAPI,
OpenAPIOperation,
OpenAPIParameter,
OpenAPIPathItem,
OpenAPIPaths,
OpenAPISchema,
Openapi,
OpenapiOperation,
OpenapiParameter,
OpenapiPathItem,
OpenapiPaths,
OpenapiSchema,
} from './openapi.js'

export interface Blueprint {
Expand Down Expand Up @@ -121,10 +121,8 @@ interface ObjectProperty extends BaseProperty {

type Method = 'GET' | 'POST' | 'PUT' | 'DELETE' | 'PATCH'

type LowercaseMethod = Lowercase<Method>

export interface TypesModule {
openapi: OpenAPI
openapi: Openapi
}

export const createBlueprint = ({ openapi }: TypesModule): Blueprint => {
Expand All @@ -144,7 +142,7 @@ export const createBlueprint = ({ openapi }: TypesModule): Blueprint => {
}

const createRoutes = (
paths: OpenAPIPaths,
paths: OpenapiPaths,
isFakeData: boolean,
targetPath: string,
): Route[] => {
Expand All @@ -153,7 +151,7 @@ const createRoutes = (
.map(([path, pathItem]) => createRoute(path, pathItem))
}

const createRoute = (path: string, pathItem: OpenAPIPathItem): Route => {
const createRoute = (path: string, pathItem: OpenapiPathItem): Route => {
const pathParts = path.split('/')
const routePath = `/${pathParts.slice(1, -1).join('/')}`

Expand All @@ -167,20 +165,20 @@ const createRoute = (path: string, pathItem: OpenAPIPathItem): Route => {

const createEndpoints = (
path: string,
pathItem: OpenAPIPathItem,
pathItem: OpenapiPathItem,
): Endpoint[] => {
return Object.entries(pathItem)
.filter(
([, operation]) => typeof operation === 'object' && operation !== null,
)
.map(([method, operation]) =>
createEndpoint(method, operation as OpenAPIOperation, path),
createEndpoint(method as Method, operation as OpenapiOperation, path),
)
}

const createEndpoint = (
method: string,
operation: OpenAPIOperation,
method: Method,
operation: OpenapiOperation,
path: string,
): Endpoint => {
const pathParts = path.split('/')
Expand All @@ -190,7 +188,7 @@ const createEndpoint = (
name:
'operationId' in operation && typeof operation.operationId === 'string'
? operation.operationId
: `${path.replace(/\//g, '')}${method.charAt(0).toUpperCase() + method.slice(1).toLowerCase()}`,
: `${path.replace(/\//g, '')}${method.charAt(0).toUpperCase()}${method.slice(1).toLowerCase()}`,
path: endpointPath,
description:
'description' in operation && typeof operation.description === 'string'
Expand All @@ -207,15 +205,16 @@ const createEndpoint = (
}
}

const createParameters = (operation: OpenAPIOperation): Parameter[] => {
return 'parameters' in operation && Array.isArray(operation.parameters)
? operation.parameters
.filter((param) => typeof param === 'object' && param !== null)
.map(createParameter)
: []
const createParameters = (operation: OpenapiOperation): Parameter[] => {
if ('parameters' in operation && Array.isArray(operation.parameters)) {
return operation.parameters
.filter((param) => typeof param === 'object' && param !== null)
.map(createParameter)
}
return []
}

const createParameter = (param: OpenAPIParameter): Parameter => {
const createParameter = (param: OpenapiParameter): Parameter => {
return {
name: 'name' in param && typeof param.name === 'string' ? param.name : '',
isRequired:
Expand All @@ -233,12 +232,10 @@ const createParameter = (param: OpenAPIParameter): Parameter => {
}

const createRequest = (
method: string,
operation: OpenAPIOperation,
method: Method,
operation: OpenapiOperation,
): Request => {
const uppercaseMethod = openapiMethodToMethod(
method.toLowerCase() as LowercaseMethod,
)
const uppercaseMethod = openapiMethodToMethod(method)

return {
methods: [uppercaseMethod],
Expand All @@ -249,7 +246,7 @@ const createRequest = (
}

const createResources = (
schemas: OpenAPI['components']['schemas'],
schemas: Openapi['components']['schemas'],
isFakeData: boolean,
targetSchema: string,
): Record<string, Resource> => {
Expand All @@ -272,14 +269,14 @@ const createResources = (
}, {})
}

const createResponse = (responses: OpenAPIOperation['responses']): Response => {
if (typeof responses !== 'object' || responses === null) {
return { responseType: 'void', description: 'No description available' }
const createResponse = (responses: OpenapiOperation['responses']): Response => {
if (responses === null) {
return { responseType: 'void', description: '' }
}

const okResponse = responses['200']
if (typeof okResponse !== 'object' || okResponse === null) {
return { responseType: 'void', description: 'No description available' }
return { responseType: 'void', description: '' }
}

const content = 'content' in okResponse ? okResponse.content : null
Expand All @@ -290,13 +287,13 @@ const createResponse = (responses: OpenAPIOperation['responses']): Response => {
'description' in okResponse &&
typeof okResponse.description === 'string'
? okResponse.description
: 'No description available',
: '',
}
}

const jsonContent =
'application/json' in content ? content['application/json'] : null
if (typeof jsonContent !== 'object' || jsonContent === null) {
if (jsonContent === null) {
return {
responseType: 'void',
description:
Expand All @@ -308,7 +305,7 @@ const createResponse = (responses: OpenAPIOperation['responses']): Response => {
}

const schema = 'schema' in jsonContent ? jsonContent.schema : null
if (typeof schema !== 'object' || schema === null) {
if (schema === null) {
return {
responseType: 'void',
description:
Expand Down Expand Up @@ -383,10 +380,10 @@ const createResponse = (responses: OpenAPIOperation['responses']): Response => {
}

const createProperties = (
properties: Record<string, OpenAPISchema>,
properties: Record<string, OpenapiSchema>,
): Property[] => {
return Object.entries(properties).map(([name, prop]): Property => {
if (typeof prop !== 'object' || prop === null) {
if (prop === null) {
return {
name,
type: 'string',
Expand Down Expand Up @@ -431,7 +428,7 @@ const createProperties = (
})
}

const openapiMethodToMethod = (openapiMethod: LowercaseMethod): Method => {
const openapiMethodToMethod = (openapiMethod: string): Method => {
switch (openapiMethod) {
case 'get':
return 'GET'
Expand All @@ -443,5 +440,7 @@ const openapiMethodToMethod = (openapiMethod: LowercaseMethod): Method => {
return 'DELETE'
case 'patch':
return 'PATCH'
default:
return 'POST'
}
}
70 changes: 35 additions & 35 deletions src/lib/openapi.ts
Original file line number Diff line number Diff line change
@@ -1,82 +1,82 @@
export interface OpenAPI {
export interface Openapi {
openapi: string
info: OpenAPIInfo
servers: OpenAPIServer[]
tags: OpenAPITag[]
paths: OpenAPIPaths
components: OpenAPIComponents
info: OpenapiInfo
servers: OpenapiServer[]
tags: OpenapiTag[]
paths: OpenapiPaths
components: OpenapiComponents
}

export interface OpenAPIInfo {
export interface OpenapiInfo {
title: string
version: string
}

export interface OpenAPIServer {
export interface OpenapiServer {
url: string
}

export interface OpenAPITag {
export interface OpenapiTag {
name: string
description: string
}

export type OpenAPIPaths = Record<string, OpenAPIPathItem>
export type OpenapiPaths = Record<string, OpenapiPathItem>

export interface OpenAPIPathItem {
get?: OpenAPIOperation
post?: OpenAPIOperation
put?: OpenAPIOperation
delete?: OpenAPIOperation
patch?: OpenAPIOperation
export interface OpenapiPathItem {
get?: OpenapiOperation
post?: OpenapiOperation
put?: OpenapiOperation
delete?: OpenapiOperation
patch?: OpenapiOperation
}

export interface OpenAPIOperation {
export interface OpenapiOperation {
operationId: string
summary?: string
description?: string
parameters?: OpenAPIParameter[]
requestBody?: OpenAPIRequestBody
responses: Record<string, OpenAPIResponse>
parameters?: OpenapiParameter[]
requestBody?: OpenapiRequestBody
responses: Record<string, OpenapiResponse>
tags?: string[]
security?: OpenAPISecurity[]
security?: OpenapiSecurity[]
}

export interface OpenAPIParameter {
export interface OpenapiParameter {
name: string
in: 'query' | 'header' | 'path' | 'cookie'
description?: string
required?: boolean
schema: OpenAPISchema
schema: OpenapiSchema
}

export interface OpenAPIRequestBody {
content: Record<string, OpenAPIMediaType>
export interface OpenapiRequestBody {
content: Record<string, OpenapiMediaType>
description?: string
required?: boolean
}

export interface OpenAPIResponse {
export interface OpenapiResponse {
description: string
content?: Record<string, OpenAPIMediaType>
content?: Record<string, OpenapiMediaType>
}

export interface OpenAPIMediaType {
schema: OpenAPISchema
export interface OpenapiMediaType {
schema: OpenapiSchema
}

export interface OpenAPISchema {
export interface OpenapiSchema {
type: 'object' | 'array' | 'string' | 'number' | 'integer' | 'boolean'
properties?: Record<string, OpenAPISchema>
items?: OpenAPISchema
properties?: Record<string, OpenapiSchema>
items?: OpenapiSchema
$ref?: string
required?: string[]
format?: string
description?: string
}

export interface OpenAPIComponents {
schemas: Record<string, OpenAPISchema>
export interface OpenapiComponents {
schemas: Record<string, OpenapiSchema>
}

export type OpenAPISecurity = Record<string, string[]>
export type OpenapiSecurity = Record<string, string[]>
11 changes: 3 additions & 8 deletions test/blueprint.test.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,11 @@
import test from 'ava'

import { createBlueprint, type TypesModule } from '@seamapi/blueprint'

import type { OpenAPI } from 'lib/openapi.js'
import { createBlueprint } from '@seamapi/blueprint'

import * as types from './fixtures/types/index.js'

const typesModule: TypesModule = {
openapi: types.openapi as unknown as OpenAPI,
}

test('createBlueprint', (t) => {
const blueprint = createBlueprint(typesModule)
// @ts-expect-error Remove once the fixture is propely typed
const blueprint = createBlueprint(types)
t.snapshot(blueprint, 'blueprint')
})
4 changes: 2 additions & 2 deletions test/seam-blueprint.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,9 +3,9 @@ import test from 'ava'

import { createBlueprint } from '@seamapi/blueprint'

import type { OpenAPI } from 'lib/openapi.js'
import type { Openapi } from 'lib/openapi.js'

test('createBlueprint', (t) => {
const blueprint = createBlueprint({ openapi: openapi as unknown as OpenAPI })
const blueprint = createBlueprint({ openapi: openapi as unknown as Openapi })
t.snapshot(blueprint, 'blueprint')
})

0 comments on commit 78ec7d3

Please sign in to comment.