Skip to content

Commit 4df5b8b

Browse files
committed
fix: update api context format (#38)
1 parent 6f0ff12 commit 4df5b8b

File tree

8 files changed

+25
-43
lines changed

8 files changed

+25
-43
lines changed

lib/2019.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -68,6 +68,7 @@ export {
6868
AsyncValidateFunction,
6969
ErrorObject,
7070
ErrorNoParams,
71+
Context,
7172
} from "./types"
7273

7374
export {Plugin, Options, CodeOptions, InstanceOptions, Logger, ErrorsTextOptions} from "./core"

lib/2020.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -62,6 +62,7 @@ export {
6262
AsyncValidateFunction,
6363
ErrorObject,
6464
ErrorNoParams,
65+
Context,
6566
} from "./types"
6667

6768
export {Plugin, Options, CodeOptions, InstanceOptions, Logger, ErrorsTextOptions} from "./core"

lib/ajv.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -57,6 +57,7 @@ export {
5757
SchemaValidateFunction,
5858
ErrorObject,
5959
ErrorNoParams,
60+
Context,
6061
} from "./types"
6162

6263
export {Plugin, Options, CodeOptions, InstanceOptions, Logger, ErrorsTextOptions} from "./core"

lib/types/index.ts

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -242,3 +242,7 @@ export interface UriResolver {
242242
resolve(base: string, path: string): string
243243
serialize(component: URIComponent): string
244244
}
245+
246+
export interface Context {
247+
apiContext?: "request" | "response"
248+
}

lib/vocabularies/oasContext.ts

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -13,15 +13,15 @@ export function getSkipCondition(schema: AnySchemaObject, prop: string): Code |
1313
if (!hasReadOnly && !hasWriteOnly) return undefined
1414

1515
const conditions: Code[] = []
16-
const oasContext = _`typeof ${N.this} == "object" && ${N.this} && ${N.this}.oas`
16+
const apiContext = _`typeof ${N.this} == "object" && ${N.this} && ${N.this}.apiContext`
1717

1818
if (hasReadOnly) {
19-
conditions.push(_`${oasContext} && ${N.this}.oas.mode === "request"`)
19+
conditions.push(_`${apiContext} === "request"`)
2020
}
2121

2222
if (hasWriteOnly) {
23-
conditions.push(_`${oasContext} && ${N.this}.oas.mode === "response"`)
23+
conditions.push(_`${apiContext} === "response"`)
2424
}
2525

26-
return conditions.length === 1 ? conditions[0] : or(...conditions)
26+
return or(...conditions)
2727
}

lib/vocabularies/validation/readOnly.ts

Lines changed: 3 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,7 @@ import {_, str} from "../../compile/codegen"
44
import N from "../../compile/names"
55

66
const error: KeywordErrorDefinition = {
7-
message: ({params}) =>
8-
str`must NOT be present in ${params.mode || "this context"}${
9-
params.location ? str` (${params.location})` : ""
10-
}`,
11-
params: ({params}) => _`{mode: ${params.mode}, location: ${params.location}}`,
7+
message: () => str`must NOT be present in request context`,
128
}
139

1410
const def: CodeKeywordDefinition = {
@@ -18,13 +14,9 @@ const def: CodeKeywordDefinition = {
1814
code(cxt: KeywordCxt) {
1915
if (cxt.schema !== true) return
2016

21-
const mode = _`(${N.this} && ${N.this}.oas ? ${N.this}.oas.mode : undefined)`
22-
const location = _`(${N.this} && ${N.this}.oas ? ${N.this}.oas.location : undefined)`
23-
cxt.setParams({mode, location})
17+
const apiContext = _`(${N.this} && ${N.this}.apiContext)`
2418

25-
cxt.fail(
26-
_`typeof ${N.this} == "object" && ${N.this} && ${N.this}.oas && ${N.this}.oas.mode === "request"`
27-
)
19+
cxt.fail(_`${apiContext} === "request"`)
2820
},
2921
}
3022

lib/vocabularies/validation/writeOnly.ts

Lines changed: 4 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -4,11 +4,7 @@ import {_, str} from "../../compile/codegen"
44
import N from "../../compile/names"
55

66
const error: KeywordErrorDefinition = {
7-
message: ({params}) =>
8-
str`must NOT be present in ${params.mode || "this context"}${
9-
params.location ? str` (${params.location})` : ""
10-
}`,
11-
params: ({params}) => _`{mode: ${params.mode}, location: ${params.location}}`,
7+
message: () => str`must NOT be present in response context`,
128
}
139

1410
const def: CodeKeywordDefinition = {
@@ -17,12 +13,9 @@ const def: CodeKeywordDefinition = {
1713
error,
1814
code(cxt: KeywordCxt) {
1915
if (cxt.schema !== true) return
20-
const mode = _`(${N.this} && ${N.this}.oas ? ${N.this}.oas.mode : undefined)`
21-
const location = _`(${N.this} && ${N.this}.oas ? ${N.this}.oas.location : undefined)`
22-
cxt.setParams({mode, location})
23-
cxt.fail(
24-
_`typeof ${N.this} == "object" && ${N.this} && ${N.this}.oas && ${N.this}.oas.mode === "response"`
25-
)
16+
const apiContext = _`(${N.this} && ${N.this}.apiContext)`
17+
18+
cxt.fail(_`${apiContext} === "response"`)
2619
},
2720
}
2821

spec/validation/read-write.spec.ts

Lines changed: 7 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,9 @@
1-
import type {DataValidationCxt} from "../../lib/types"
1+
import type {DataValidationCxt, Context} from "../../lib/types"
22
import Ajv from "../ajv"
33
import chai from "../chai"
44

55
chai.should()
66

7-
type OasMode = "request" | "response"
8-
97
function buildContext(data: unknown): DataValidationCxt {
108
const dynamicAnchors: DataValidationCxt["dynamicAnchors"] = {}
119
return {
@@ -21,17 +19,9 @@ function getAjv() {
2119
return new Ajv({passContext: true})
2220
}
2321

24-
function getOasContext(mode: OasMode, location?: "requestBody" | "responseBody") {
25-
return {oas: {mode, location}}
26-
}
27-
2822
type Validate = ReturnType<InstanceType<typeof Ajv>["compile"]>
2923

30-
function expectValid(
31-
validate: Validate,
32-
data: unknown,
33-
ctx?: {oas: {mode: OasMode; location?: "requestBody" | "responseBody"}}
34-
) {
24+
function expectValid(validate: Validate, data: unknown, ctx?: Context) {
3525
const valid = ctx ? validate.call(ctx, data, buildContext(data)) : validate(data)
3626
valid.should.equal(true)
3727
}
@@ -40,7 +30,7 @@ function expectInvalid(
4030
validate: Validate,
4131
data: unknown,
4232
keyword: "readOnly" | "writeOnly" | "required",
43-
ctx?: {oas: {mode: OasMode; location?: "requestBody" | "responseBody"}}
33+
ctx?: Context
4434
) {
4535
const valid = ctx ? validate.call(ctx, data, buildContext(data)) : validate(data)
4636
valid.should.equal(false)
@@ -78,7 +68,7 @@ describe("readOnly/writeOnly", () => {
7868

7969
it("should skip readOnly in request context and still require writeOnly", () => {
8070
const validate = getAjv().compile(schemaWithRequired)
81-
const requestCtx = getOasContext("request", "requestBody")
71+
const requestCtx: Context = {apiContext: "request"}
8272

8373
expectValid(validate, {password: "secret"}, requestCtx)
8474
expectInvalid(validate, {id: "1", password: "secret"}, "readOnly", requestCtx)
@@ -87,7 +77,7 @@ describe("readOnly/writeOnly", () => {
8777

8878
it("should skip writeOnly in response context and still require readOnly", () => {
8979
const validate = getAjv().compile(schemaWithRequired)
90-
const responseCtx = getOasContext("response", "responseBody")
80+
const responseCtx: Context = {apiContext: "response"}
9181

9282
expectValid(validate, {id: "1"}, responseCtx)
9383
expectInvalid(validate, {id: "1", password: "secret"}, "writeOnly", responseCtx)
@@ -98,14 +88,14 @@ describe("readOnly/writeOnly", () => {
9888
describe("presence validation with context", () => {
9989
it("should reject readOnly in request context", () => {
10090
const validate = getAjv().compile(baseSchema)
101-
const requestCtx = getOasContext("request", "requestBody")
91+
const requestCtx: Context = {apiContext: "request"}
10292

10393
expectInvalid(validate, {id: "1"}, "readOnly", requestCtx)
10494
})
10595

10696
it("should reject writeOnly in response context", () => {
10797
const validate = getAjv().compile(baseSchema)
108-
const responseCtx = getOasContext("response", "responseBody")
98+
const responseCtx: Context = {apiContext: "response"}
10999

110100
expectInvalid(validate, {password: "secret"}, "writeOnly", responseCtx)
111101
})

0 commit comments

Comments
 (0)