Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add support for readOnly and writeOnly fields #397

Open
wants to merge 5 commits into
base: master
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 9 additions & 1 deletion packages/openapi-to-graphql/lib/schema_builder.js

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion packages/openapi-to-graphql/lib/schema_builder.js.map

Large diffs are not rendered by default.

2 changes: 2 additions & 0 deletions packages/openapi-to-graphql/lib/types/oas3.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,8 @@ export declare type SchemaObject = {
anyOf?: (SchemaObject | ReferenceObject)[];
oneOf?: (SchemaObject | ReferenceObject)[];
not?: (SchemaObject | ReferenceObject)[];
readOnly?: boolean;
writeOnly?: boolean;
};
export declare type ReferenceObject = {
$ref: string;
Expand Down
12 changes: 11 additions & 1 deletion packages/openapi-to-graphql/src/schema_builder.ts
Original file line number Diff line number Diff line change
Expand Up @@ -512,7 +512,7 @@ function createOrReuseList<TSource, TContext, TArgs>({
}
return listObjectType
} else {
throw new Error(`Cannot create list item object type '${itemsName}' in list
throw new Error(`Cannot create list item object type '${itemsName}' in list
'${name}' with schema '${JSON.stringify(itemsSchema)}'`)
}
}
Expand Down Expand Up @@ -616,6 +616,16 @@ function createFields<TSource, TContext, TArgs>({
const fieldTypeDefinition = fieldTypeDefinitions[fieldTypeKey]
const fieldSchema = fieldTypeDefinition.schema

// readOnly fields should not be included for Input types
if (isInputObjectType && fieldSchema?.readOnly) {
continue
}

// writeOnly fields should not be included for non-Input types
if (!isInputObjectType && fieldSchema?.writeOnly) {
continue
}

// Get object type describing the property
const objectType = getGraphQLType({
def: fieldTypeDefinition,
Expand Down
2 changes: 2 additions & 0 deletions packages/openapi-to-graphql/src/types/oas3.ts
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,8 @@ export type SchemaObject = {
anyOf?: (SchemaObject | ReferenceObject)[]
oneOf?: (SchemaObject | ReferenceObject)[]
not?: (SchemaObject | ReferenceObject)[]
readOnly?: boolean
writeOnly?: boolean
}

export type ReferenceObject = {
Expand Down
24 changes: 22 additions & 2 deletions packages/openapi-to-graphql/test/example_api7.test.ts
Original file line number Diff line number Diff line change
@@ -1,6 +1,14 @@
'use strict'

import { graphql, parse, validate, execute, subscribe } from 'graphql'
import {
graphql,
parse,
validate,
execute,
subscribe,
GraphQLSchema,
GraphQLObjectType
} from 'graphql'
import { afterAll, beforeAll, expect, test } from '@jest/globals'

import { createServer } from 'http'
Expand All @@ -23,7 +31,7 @@ const MQTT_PORT = 1885
oas.servers[0].variables.port.default = String(HTTP_PORT)
oas.servers[1].variables.port.default = String(MQTT_PORT)

let createdSchema
let createdSchema: GraphQLSchema
let wsServer
let mqttClient
let subscriptionServer
Expand Down Expand Up @@ -182,3 +190,15 @@ test('Receive data from the subscription after creating a new instance', () => {
}, 500)
})
})

test('should filter out readOnly properties from Input types', () => {
const device = createdSchema.getType('Device') as GraphQLObjectType
const deviceProps = Object.keys(device.getFields())

expect(deviceProps).toEqual(['id', 'name', 'status', 'userName'])

const deviceInput = createdSchema.getType('DeviceInput') as GraphQLObjectType
const deviceInputProps = Object.keys(deviceInput.getFields())

expect(deviceInputProps).toEqual(['name', 'status', 'userName'])
})
4 changes: 4 additions & 0 deletions packages/openapi-to-graphql/test/fixtures/example_oas7.json
Original file line number Diff line number Diff line change
Expand Up @@ -177,6 +177,10 @@
"type": "object",
"description": "A device is an object connected to the network",
"properties": {
"id": {
"type": "string",
"readOnly": true
},
"name": {
"type": "string",
"description": "The device name in the network"
Expand Down