chore(style): codebase em-dash sweep + minor layout polish
Replaces every em-dash and en-dash with regular ASCII hyphens across comments, JSX strings, and dev-facing logs. Mostly cosmetic but stops the inconsistent mix that crept in over the last few months (some files used em-dashes in comments, others didn't, some used both). Bundles two small dashboard-layout tweaks that touch a couple of already-modified files: - (dashboard)/layout.tsx main padding goes from p-6 to pt-3 px-6 pb-6 so page content sits closer to the topbar. - Sidebar now receives the ports list it needs for the footer port switcher. Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -10,7 +10,7 @@ import { runAlertEngineForPorts } from '@/lib/services/alert-engine';
|
||||
* exercised by the realapi socket fanout test.
|
||||
*
|
||||
* Requires super_admin or per-port admin permissions; the engine itself
|
||||
* is idempotent — duplicate runs only re-evaluate, never duplicate rows.
|
||||
* is idempotent - duplicate runs only re-evaluate, never duplicate rows.
|
||||
*/
|
||||
export const POST = withAuth(async (_req, ctx) => {
|
||||
try {
|
||||
|
||||
@@ -5,7 +5,7 @@ import { errorResponse } from '@/lib/errors';
|
||||
import { checkDocumensoHealth } from '@/lib/services/documenso-client';
|
||||
|
||||
/**
|
||||
* Admin probe — calls Documenso /api/v1/health using the port's effective
|
||||
* Admin probe - calls Documenso /api/v1/health using the port's effective
|
||||
* config. Used by the "Test connection" button on /admin/documenso.
|
||||
*/
|
||||
export const POST = withAuth(
|
||||
|
||||
@@ -40,7 +40,7 @@ export async function listHandler(_req: Request, ctx: AuthContext): Promise<Next
|
||||
.map((p) => {
|
||||
const a = clientById.get(p.clientAId);
|
||||
const b = clientById.get(p.clientBId);
|
||||
if (!a || !b) return null; // FK orphan — shouldn't happen, but be defensive
|
||||
if (!a || !b) return null; // FK orphan - shouldn't happen, but be defensive
|
||||
// Skip pairs where one side has already been merged or archived.
|
||||
if (a.mergedIntoClientId || b.mergedIntoClientId) return null;
|
||||
return {
|
||||
|
||||
@@ -9,7 +9,7 @@ import { createCrmInvite, listCrmInvites } from '@/lib/services/crm-invite.servi
|
||||
export const GET = withAuth(
|
||||
withPermission('admin', 'manage_users', async (_req, ctx) => {
|
||||
try {
|
||||
// crm_user_invites is a global table (no per-port column) — invites
|
||||
// crm_user_invites is a global table (no per-port column) - invites
|
||||
// mint better-auth users that may later be assigned roles in any
|
||||
// port. Listing it cross-tenant would let a port-A director
|
||||
// enumerate pending invitee emails, names, and isSuperAdmin flags
|
||||
|
||||
@@ -13,7 +13,7 @@ const schema = z.object({
|
||||
apiKey: z.string().min(1),
|
||||
});
|
||||
|
||||
// `manage_settings`-gated for parity with the parent OCR settings route —
|
||||
// `manage_settings`-gated for parity with the parent OCR settings route -
|
||||
// triggers outbound AI provider auth requests using a caller-supplied key.
|
||||
export const POST = withAuth(
|
||||
withPermission('admin', 'manage_settings', async (req) => {
|
||||
|
||||
@@ -17,12 +17,12 @@ import { previewAdminTemplateSchema } from '@/lib/validators/document-templates'
|
||||
* POST /api/v1/admin/templates/preview
|
||||
*
|
||||
* Generates a preview PDF from a TipTap JSON content block.
|
||||
* Returns { data: { pdfBase64: string } } — the client can render this
|
||||
* Returns { data: { pdfBase64: string } } - the client can render this
|
||||
* in an <iframe src="data:application/pdf;base64,..."> or open in a new tab.
|
||||
*
|
||||
* Body:
|
||||
* content: TipTap JSON document
|
||||
* sampleData?: Record<string, string> — variable substitutions
|
||||
* sampleData?: Record<string, string> - variable substitutions
|
||||
*/
|
||||
export const POST = withAuth(
|
||||
withPermission('documents', 'manage', async (req, _ctx) => {
|
||||
@@ -60,10 +60,7 @@ export const POST = withAuth(
|
||||
/**
|
||||
* Deeply substitutes {{variable}} tokens in all text nodes of a TipTap doc.
|
||||
*/
|
||||
function substituteInDoc(
|
||||
node: TipTapNode,
|
||||
data: Record<string, string>,
|
||||
): TipTapNode {
|
||||
function substituteInDoc(node: TipTapNode, data: Record<string, string>): TipTapNode {
|
||||
if (node.type === 'text' && node.text) {
|
||||
return { ...node, text: substituteVariables(node.text, data) };
|
||||
}
|
||||
|
||||
@@ -3,7 +3,7 @@ import { withAuth, withPermission } from '@/lib/api/helpers';
|
||||
import { getHandler, patchHandler, deleteHandler } from './handlers';
|
||||
|
||||
export const GET = withAuth(withPermission('reservations', 'view', getHandler));
|
||||
// PATCH cannot use `withPermission` wrapper — the required permission depends
|
||||
// PATCH cannot use `withPermission` wrapper - the required permission depends
|
||||
// on the `action` field in the body. `requirePermission` is called inside the
|
||||
// handler after the body is parsed.
|
||||
export const PATCH = withAuth(patchHandler);
|
||||
|
||||
@@ -40,7 +40,7 @@ export const PUT = withAuth(
|
||||
}),
|
||||
);
|
||||
|
||||
// PATCH /api/v1/berths/[id]/waiting-list — reorder a single entry
|
||||
// PATCH /api/v1/berths/[id]/waiting-list - reorder a single entry
|
||||
export const PATCH = withAuth(
|
||||
withPermission('berths', 'manage_waiting_list', async (req, ctx, params) => {
|
||||
try {
|
||||
|
||||
@@ -4,7 +4,7 @@ import { withAuth, withPermission } from '@/lib/api/helpers';
|
||||
import { getBerthOptions } from '@/lib/services/berths.service';
|
||||
import { errorResponse } from '@/lib/errors';
|
||||
|
||||
// GET /api/v1/berths/options — lightweight list for selects/comboboxes
|
||||
// GET /api/v1/berths/options - lightweight list for selects/comboboxes
|
||||
export const GET = withAuth(
|
||||
withPermission('berths', 'view', async (req, ctx) => {
|
||||
try {
|
||||
|
||||
@@ -19,7 +19,7 @@ const inviteSchema = z.object({
|
||||
*
|
||||
* Admin creates a portal account for a client and triggers the activation
|
||||
* email. Idempotent in spirit: if a portal user already exists for the
|
||||
* email, returns 409 — the admin can resend the activation via
|
||||
* email, returns 409 - the admin can resend the activation via
|
||||
* ?action=resend.
|
||||
*/
|
||||
export const POST = withAuth(
|
||||
|
||||
@@ -44,7 +44,7 @@ export async function getMatchCandidatesHandler(
|
||||
const nameResult = rawName ? normalizeName(rawName) : null;
|
||||
|
||||
// If the caller didn't give us anything useful to match on, return empty
|
||||
// — short-circuit rather than scan every client for nothing.
|
||||
// - short-circuit rather than scan every client for nothing.
|
||||
if (!email && !phoneResult?.e164 && !nameResult?.surnameToken) {
|
||||
return NextResponse.json({ data: [] });
|
||||
}
|
||||
@@ -122,7 +122,7 @@ export async function getMatchCandidatesHandler(
|
||||
mediumScore: 50,
|
||||
});
|
||||
|
||||
// Only return medium+ — low-confidence noise isn't useful at the
|
||||
// Only return medium+ - low-confidence noise isn't useful at the
|
||||
// create-form layer (background scoring queue picks those up).
|
||||
const useful = matches.filter((m) => m.confidence !== 'low');
|
||||
if (useful.length === 0) {
|
||||
|
||||
@@ -7,7 +7,7 @@ import { errorResponse } from '@/lib/errors';
|
||||
import { mergeDuplicate } from '@/lib/services/expense-dedup.service';
|
||||
|
||||
const mergeSchema = z.object({
|
||||
/** Surviving expense id — typically the row's existing `duplicateOf` pointer. */
|
||||
/** Surviving expense id - typically the row's existing `duplicateOf` pointer. */
|
||||
targetId: z.string().min(1),
|
||||
});
|
||||
|
||||
|
||||
@@ -51,7 +51,7 @@ export const POST = withAuth(
|
||||
});
|
||||
}
|
||||
|
||||
// Per-port budget gate — refuse the call before we spend tokens
|
||||
// Per-port budget gate - refuse the call before we spend tokens
|
||||
// when the port has already hit its hard cap, or when the request
|
||||
// would push it past the cap. Soft-cap warnings ride along on the
|
||||
// success response so the UI can show a banner without blocking.
|
||||
@@ -99,7 +99,7 @@ export const POST = withAuth(
|
||||
});
|
||||
} catch (err) {
|
||||
logger.error({ err, provider: config.provider }, 'OCR provider call failed');
|
||||
// Provider hiccup — degrade to manual entry rather than 500-ing.
|
||||
// Provider hiccup - degrade to manual entry rather than 500-ing.
|
||||
return NextResponse.json({
|
||||
data: {
|
||||
parsed: EMPTY,
|
||||
|
||||
@@ -16,7 +16,7 @@ export const POST = withAuth(
|
||||
try {
|
||||
const body = await parseBody(req, createFolderSchema);
|
||||
|
||||
// Sanitize path — no null bytes, no path traversal
|
||||
// Sanitize path - no null bytes, no path traversal
|
||||
const safePath = body.path
|
||||
.replace(/\x00/g, '')
|
||||
.replace(/\.\.\//g, '')
|
||||
|
||||
@@ -20,7 +20,7 @@ export const GET = withAuth(
|
||||
}),
|
||||
);
|
||||
|
||||
// POST /api/v1/interests/[id]/recommendations — add manual recommendation
|
||||
// POST /api/v1/interests/[id]/recommendations - add manual recommendation
|
||||
export const POST = withAuth(
|
||||
withPermission('interests', 'edit', async (req, ctx, params) => {
|
||||
try {
|
||||
|
||||
@@ -12,9 +12,9 @@ import { stageLabel } from '@/lib/constants';
|
||||
|
||||
const OUTCOME_LABELS: Record<string, string> = {
|
||||
won: 'Won',
|
||||
lost_other_marina: 'Lost — went to another marina',
|
||||
lost_unqualified: 'Lost — unqualified',
|
||||
lost_no_response: 'Lost — no response',
|
||||
lost_other_marina: 'Lost - went to another marina',
|
||||
lost_unqualified: 'Lost - unqualified',
|
||||
lost_no_response: 'Lost - no response',
|
||||
cancelled: 'Cancelled',
|
||||
};
|
||||
|
||||
@@ -187,7 +187,7 @@ function buildAuditDescription(
|
||||
const outcomeKey = (newValue?.outcome as string | undefined) ?? '';
|
||||
const label = OUTCOME_LABELS[outcomeKey] ?? outcomeKey ?? 'Closed';
|
||||
const reason = (newValue?.reason as string | undefined) ?? '';
|
||||
return reason ? `Marked as ${label} — ${reason}` : `Marked as ${label}`;
|
||||
return reason ? `Marked as ${label} - ${reason}` : `Marked as ${label}`;
|
||||
}
|
||||
|
||||
if (type === 'outcome_cleared') {
|
||||
@@ -200,9 +200,9 @@ function buildAuditDescription(
|
||||
const reason = (newValue.reason as string | undefined) ?? '';
|
||||
const auto = userId === 'system';
|
||||
if (auto) {
|
||||
return reason ? `${stage} (auto-advanced — ${reason})` : `Stage advanced to ${stage}`;
|
||||
return reason ? `${stage} (auto-advanced - ${reason})` : `Stage advanced to ${stage}`;
|
||||
}
|
||||
return reason ? `Stage changed to ${stage} — ${reason}` : `Stage changed to ${stage}`;
|
||||
return reason ? `Stage changed to ${stage} - ${reason}` : `Stage changed to ${stage}`;
|
||||
}
|
||||
|
||||
if (action === 'update' && newValue?.pipelineStage) {
|
||||
|
||||
@@ -18,7 +18,7 @@ export const GET = withAuth(async (req: NextRequest, ctx) => {
|
||||
|
||||
const results = await search(ctx.portId, q);
|
||||
|
||||
// Fire-and-forget — do not await
|
||||
// Fire-and-forget - do not await
|
||||
saveRecentSearch(ctx.userId, ctx.portId, q);
|
||||
|
||||
return NextResponse.json(results);
|
||||
|
||||
Reference in New Issue
Block a user