This commit is contained in:
Fang-Pen Lin
2025-11-07 09:18:17 -08:00
parent 223835d141
commit 6064b39c05
2 changed files with 9 additions and 18 deletions
+2 -5
View File
@@ -1,6 +1,7 @@
/* eslint-disable @typescript-eslint/no-floating-promises */ /* eslint-disable @typescript-eslint/no-floating-promises */
import { z } from "zod"; import { z } from "zod";
import { AcmeBadPublicKeyError } from "@app/ee/services/pki-acme/pki-acme-errors";
import { import {
CreateAcmeAccountBodySchema, CreateAcmeAccountBodySchema,
CreateAcmeAccountResponseSchema, CreateAcmeAccountResponseSchema,
@@ -24,15 +25,11 @@ import {
RespondToAcmeChallengeResponseSchema, RespondToAcmeChallengeResponseSchema,
RespondToAcmeChallengeSchema RespondToAcmeChallengeSchema
} from "@app/ee/services/pki-acme/pki-acme-schemas"; } from "@app/ee/services/pki-acme/pki-acme-schemas";
import { TCreateAcmeAccountPayload, TRawJwsPayload } from "@app/ee/services/pki-acme/pki-acme-types"; import { TRawJwsPayload } from "@app/ee/services/pki-acme/pki-acme-types";
import { ApiDocsTags } from "@app/lib/api-docs"; import { ApiDocsTags } from "@app/lib/api-docs";
import { getConfig } from "@app/lib/config/env";
import { readLimit, writeLimit } from "@app/server/config/rateLimiter"; import { readLimit, writeLimit } from "@app/server/config/rateLimiter";
import { AcmeBadPublicKeyError } from "@app/ee/services/pki-acme/pki-acme-errors";
export const registerPkiAcmeRouter = async (server: FastifyZodProvider) => { export const registerPkiAcmeRouter = async (server: FastifyZodProvider) => {
const appCfg = getConfig();
server.addContentTypeParser("application/jose+json", { parseAs: "string" }, (_, body, done) => { server.addContentTypeParser("application/jose+json", { parseAs: "string" }, (_, body, done) => {
try { try {
const strBody = body instanceof Buffer ? body.toString() : body; const strBody = body instanceof Buffer ? body.toString() : body;
@@ -33,7 +33,6 @@ import {
TGetAcmeDirectoryResponse, TGetAcmeDirectoryResponse,
TGetAcmeOrderResponse, TGetAcmeOrderResponse,
TJwsPayload, TJwsPayload,
TJwsPayloadWithJwk,
TListAcmeOrdersResponse, TListAcmeOrdersResponse,
TPkiAcmeServiceFactory, TPkiAcmeServiceFactory,
TRawJwsPayload, TRawJwsPayload,
@@ -74,15 +73,13 @@ export const pkiAcmeServiceFactory = ({
rawJwsPayload: TRawJwsPayload, rawJwsPayload: TRawJwsPayload,
getJWK: (protectedHeader: JWSHeaderParameters) => Promise<JsonWebKey>, getJWK: (protectedHeader: JWSHeaderParameters) => Promise<JsonWebKey>,
schema: z.ZodSchema<T> schema: z.ZodSchema<T>
): Promise<TJwsPayload> => { ): Promise<TJwsPayload<T>> => {
let result: FlattenedVerifyResult; let result: FlattenedVerifyResult;
try { try {
result = await flattenedVerify(rawJwsPayload, async (protectedHeader: JWSHeaderParameters | undefined) => { result = await flattenedVerify(rawJwsPayload, async (protectedHeader: JWSHeaderParameters | undefined) => {
if (protectedHeader === undefined) { if (protectedHeader === undefined) {
throw new AcmeMalformedError({ detail: "Protected header is required" }); throw new AcmeMalformedError({ detail: "Protected header is required" });
} }
const parsedHeader = ProtectedHeaderSchema.parse(protectedHeader);
// TODO: consume the nonce here
const jwk = await getJWK(protectedHeader); const jwk = await getJWK(protectedHeader);
return await importJWK(jwk, protectedHeader.alg); return await importJWK(jwk, protectedHeader.alg);
}); });
@@ -96,15 +93,12 @@ export const pkiAcmeServiceFactory = ({
logger.error(error, "Unexpected error while verifying JWS payload"); logger.error(error, "Unexpected error while verifying JWS payload");
throw new AcmeServerInternalError({ detail: "Failed to verify JWS payload" }); throw new AcmeServerInternalError({ detail: "Failed to verify JWS payload" });
} }
const { payload: rawPayload, protectedHeader: rawProtectedHeader } = result!; const { protectedHeader: rawProtectedHeader, payload: rawPayload } = result;
const { success, data: protectedHeader } = ProtectedHeaderSchema.safeParse(rawProtectedHeader);
if (!success) {
throw new AcmeMalformedError({ detail: "Invalid protected header" });
}
const decoder = new TextDecoder();
const jsonPayload = JSON.parse(decoder.decode(rawPayload));
try { try {
const protectedHeader = ProtectedHeaderSchema.parse(rawProtectedHeader);
// TODO: consume the nonce here
const decoder = new TextDecoder();
const jsonPayload = JSON.parse(decoder.decode(rawPayload));
const payload = schema.parse(jsonPayload); const payload = schema.parse(jsonPayload);
return { return {
protectedHeader, protectedHeader,
@@ -297,7 +291,7 @@ export const pkiAcmeServiceFactory = ({
}; };
return { return {
validateCreateAcmeAccountJwsPayload, validateJwsPayload,
getAcmeDirectory, getAcmeDirectory,
getAcmeNewNonce, getAcmeNewNonce,
createAcmeAccount, createAcmeAccount,