Deploy stack su Proxmox / deploy (push) Failing after 3s
Monorepo npm con apps/public (Angular SSR), apps/private (Angular SPA), apps/api (Fastify), packages/shared e packages/styles; Medusa 2.21 in medusa/; infrastruttura Docker (Postgres PostGIS+pgvector, Redis, Caddy, backup) e workflow Gitea Actions per il deploy via SSH a ogni push su master. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com> Claude-Session: https://claude.ai/code/session_018jQyT6dR9czzGwqb7FkG6u
45 lines
1.8 KiB
TypeScript
45 lines
1.8 KiB
TypeScript
import { getTableColumns } from "drizzle-orm"
|
|
import { describe, expect, it } from "vitest"
|
|
import { emailVerificationTokens, passwordResetTokens, refreshTokens, users } from "../src/db/schema/index.js"
|
|
import { hashPassword, verifyPassword } from "../src/services/password.js"
|
|
import { generateToken, hashToken } from "../src/services/tokens.js"
|
|
|
|
describe("token opachi", () => {
|
|
it("256 bit casuali, hash SHA-256 diverso dal token", () => {
|
|
const { token, hash } = generateToken()
|
|
expect(Buffer.from(token, "base64url")).toHaveLength(32)
|
|
expect(hash).toMatch(/^[0-9a-f]{64}$/)
|
|
expect(hash).not.toContain(token)
|
|
expect(hashToken(token)).toBe(hash)
|
|
expect(generateToken().token).not.toBe(token)
|
|
})
|
|
})
|
|
|
|
describe("password", () => {
|
|
it("argon2id, verifica ok/ko, hash malformato -> false", async () => {
|
|
const h = await hashPassword("una password lunga")
|
|
expect(h.startsWith("$argon2id$")).toBe(true)
|
|
expect(await verifyPassword(h, "una password lunga")).toBe(true)
|
|
expect(await verifyPassword(h, "sbagliata")).toBe(false)
|
|
expect(await verifyPassword("non-un-hash", "x")).toBe(false)
|
|
})
|
|
})
|
|
|
|
describe("schema: niente segreti in chiaro", () => {
|
|
it.each([
|
|
["refresh_tokens", refreshTokens],
|
|
["password_reset_tokens", passwordResetTokens],
|
|
["email_verification_tokens", emailVerificationTokens],
|
|
])("%s ha solo token_hash", (_name, table) => {
|
|
const columns = Object.values(getTableColumns(table)).map((c) => c.name)
|
|
expect(columns).toContain("token_hash")
|
|
expect(columns.filter((c) => /token|secret/.test(c) && c !== "token_hash")).toEqual([])
|
|
})
|
|
|
|
it("users ha password_hash e nessuna colonna password in chiaro", () => {
|
|
const columns = Object.values(getTableColumns(users)).map((c) => c.name)
|
|
expect(columns).toContain("password_hash")
|
|
expect(columns).not.toContain("password")
|
|
})
|
|
})
|