45 lines
1.0 KiB
TypeScript
45 lines
1.0 KiB
TypeScript
export type Branch = 'askim' | 'backaplan';
|
|
|
|
export interface ValidTableId {
|
|
valid: true;
|
|
branch: Branch;
|
|
tableNumber: string;
|
|
tableIdentifier: string;
|
|
}
|
|
|
|
export interface InvalidTableId {
|
|
valid: false;
|
|
reason: 'missing' | 'format' | 'range';
|
|
}
|
|
|
|
export type ParsedTableId = ValidTableId | InvalidTableId;
|
|
|
|
const TABLE_ID_PATTERN = /^(backaplan|askim)-([0-9]{3})$/;
|
|
const MIN_TABLE = 1;
|
|
const MAX_TABLE = 40;
|
|
|
|
/** Domain rule: parse and validate QR table identifiers. */
|
|
export function parseTableId(raw: string | null | undefined): ParsedTableId {
|
|
if (!raw) {
|
|
return { valid: false, reason: 'missing' };
|
|
}
|
|
|
|
const match = raw.match(TABLE_ID_PATTERN);
|
|
if (!match) {
|
|
return { valid: false, reason: 'format' };
|
|
}
|
|
|
|
const branch = match[1] as Branch;
|
|
const tableNum = parseInt(match[2], 10);
|
|
|
|
if (tableNum < MIN_TABLE || tableNum > MAX_TABLE) {
|
|
return { valid: false, reason: 'range' };
|
|
}
|
|
|
|
return {
|
|
valid: true,
|
|
branch,
|
|
tableNumber: match[2],
|
|
tableIdentifier: raw,
|
|
};
|
|
} |