Template
1
0

feat: initial boilerplate

This commit is contained in:
2025-08-11 20:45:41 +02:00
parent d98524254f
commit 1215a98afc
148 changed files with 6935 additions and 2060 deletions

1
spec/modules/README.md Normal file
View File

@@ -0,0 +1 @@
# Modules

View File

@@ -0,0 +1,7 @@
import { BadRequestError } from "@spec/relay";
export class AuthenticationStrategyPayloadError extends BadRequestError {
constructor() {
super("Provided authentication payload is not recognized.");
}
}

8
spec/modules/auth/mod.ts Normal file
View File

@@ -0,0 +1,8 @@
import { authenticate } from "./routes/authenticate.ts";
export * from "./errors.ts";
export * from "./strategies.ts";
export const routes = {
authenticate,
};

View File

@@ -0,0 +1,9 @@
import { route } from "@spec/relay";
import { AuthenticationStrategyPayloadError } from "../errors.ts";
import { StrategyPayloadSchema } from "../strategies.ts";
export const authenticate = route
.post("/api/v1/authenticate")
.body(StrategyPayloadSchema)
.errors([AuthenticationStrategyPayloadError]);

View File

@@ -0,0 +1,51 @@
import { z } from "zod";
export const PasskeyStrategySchema = z.object({
type: z.literal("passkey").describe("Authentication strategy type for WebAuthn/Passkey"),
payload: z
.object({
id: z.string().describe("Base64URL encoded credential ID"),
rawId: z.string().describe("Raw credential ID as base64URL encoded string"),
response: z
.object({
clientDataJSON: z.string().describe("Base64URL encoded client data JSON"),
authenticatorData: z.string().describe("Base64URL encoded authenticator data"),
signature: z.string().optional().describe("Signature for authentication responses"),
userHandle: z.string().optional().describe("Optional user handle identifier"),
attestationObject: z.string().optional().describe("Attestation object for registration responses"),
})
.describe("WebAuthn response data"),
clientExtensionResults: z
.record(z.string(), z.unknown())
.default({})
.describe("Results from WebAuthn extension inputs"),
authenticatorAttachment: z
.enum(["platform", "cross-platform"])
.optional()
.describe("Type of authenticator used (platform or cross-platform)"),
})
.describe("WebAuthn credential payload"),
});
export const EmailStrategySchema = z.object({
type: z.literal("email").describe("Authentication strategy type for email"),
payload: z
.object({
email: z.email().describe("User's email address for authentication"),
})
.describe("Email authentication payload"),
});
export const PasswordStrategySchema = z.object({
type: z.literal("password").describe("Authentication strategy type for password"),
payload: z
.object({
identifier: z.string().describe("User identifier (username or email)"),
password: z.string().describe("User's password"),
})
.describe("Password authentication payload"),
});
export const StrategyPayloadSchema = z
.union([PasskeyStrategySchema, EmailStrategySchema, PasswordStrategySchema])
.describe("Union of all available authentication strategy schemas");

11
spec/modules/package.json Normal file
View File

@@ -0,0 +1,11 @@
{
"name": "@spec/modules",
"version": "0.0.0",
"private": true,
"type": "module",
"dependencies": {
"@spec/relay": "workspace:*",
"@spec/shared": "workspace:*",
"zod": "4"
}
}