@@ -7,9 +7,47 @@ const __dirname = path.dirname(fileURLToPath(import.meta.url));
|
||||
const dataDir = path.join(__dirname, '..', 'data');
|
||||
if (!fs.existsSync(dataDir)) fs.mkdirSync(dataDir, { recursive: true });
|
||||
const dbPath = process.env.DATABASE_PATH || path.join(dataDir, 'configurateur.db');
|
||||
const schemaPath = path.join(__dirname, 'schema.sql');
|
||||
|
||||
let db = null;
|
||||
|
||||
/** Création idempotente — bases anciennes sans ces tables (avant migration 014). */
|
||||
const HARDWARE_CATALOG_DDL = `
|
||||
CREATE TABLE IF NOT EXISTS blum_hardware (
|
||||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||||
code TEXT UNIQUE NOT NULL,
|
||||
name TEXT NOT NULL,
|
||||
type TEXT NOT NULL,
|
||||
variant TEXT,
|
||||
price_chf REAL NOT NULL,
|
||||
specs_json TEXT,
|
||||
image_url TEXT,
|
||||
active INTEGER DEFAULT 1
|
||||
);
|
||||
CREATE TABLE IF NOT EXISTS handle_variants (
|
||||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||||
code TEXT UNIQUE NOT NULL,
|
||||
name TEXT NOT NULL,
|
||||
style TEXT,
|
||||
length_mm INTEGER,
|
||||
price_chf REAL NOT NULL,
|
||||
image_url TEXT,
|
||||
active INTEGER DEFAULT 1
|
||||
);
|
||||
CREATE TABLE IF NOT EXISTS hinge_variants (
|
||||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||||
code TEXT UNIQUE NOT NULL,
|
||||
name TEXT NOT NULL,
|
||||
type TEXT NOT NULL,
|
||||
brand TEXT DEFAULT 'Blum',
|
||||
price_chf REAL NOT NULL,
|
||||
active INTEGER DEFAULT 1
|
||||
);
|
||||
CREATE INDEX IF NOT EXISTS idx_blum_hardware_type ON blum_hardware(type);
|
||||
CREATE INDEX IF NOT EXISTS idx_handle_variants_style ON handle_variants(style);
|
||||
CREATE INDEX IF NOT EXISTS idx_hinge_variants_type ON hinge_variants(type);
|
||||
`;
|
||||
|
||||
function toSqlitePlaceholders(sql) {
|
||||
return sql.replace(/\$(\d+)/g, '?');
|
||||
}
|
||||
@@ -31,6 +69,18 @@ async function getDb() {
|
||||
buffer = fs.readFileSync(dbPath);
|
||||
}
|
||||
db = new SQL.Database(buffer || null);
|
||||
try {
|
||||
// Ensure full schema exists for legacy/partial DB files.
|
||||
if (fs.existsSync(schemaPath)) {
|
||||
const schemaSql = fs.readFileSync(schemaPath, 'utf8');
|
||||
db.exec(schemaSql);
|
||||
}
|
||||
db.exec(HARDWARE_CATALOG_DDL);
|
||||
const data = db.export();
|
||||
fs.writeFileSync(dbPath, Buffer.from(data));
|
||||
} catch (e) {
|
||||
console.error('[db] ensureHardwareCatalogTables:', e.message);
|
||||
}
|
||||
return db;
|
||||
}
|
||||
|
||||
|
||||
@@ -0,0 +1,2 @@
|
||||
-- Add price_chf to formex_dimensions so each size variant can have its own price
|
||||
ALTER TABLE formex_dimensions ADD COLUMN price_chf REAL;
|
||||
@@ -0,0 +1,16 @@
|
||||
-- Migration 007: Suppliers table for order voucher emails
|
||||
|
||||
CREATE TABLE IF NOT EXISTS suppliers (
|
||||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||||
code TEXT UNIQUE NOT NULL,
|
||||
name TEXT NOT NULL,
|
||||
email TEXT NOT NULL,
|
||||
type TEXT NOT NULL, -- 'panels', 'hardware', 'handles', 'other'
|
||||
active INTEGER DEFAULT 1,
|
||||
created_at TEXT DEFAULT (datetime('now'))
|
||||
);
|
||||
|
||||
-- Seed default suppliers
|
||||
INSERT OR IGNORE INTO suppliers (code, name, email, type) VALUES
|
||||
('formex', 'Formex', '[email protected]', 'panels'),
|
||||
('blum', 'Blum Switzerland', '[email protected]', 'hardware');
|
||||
@@ -91,6 +91,7 @@ CREATE TABLE IF NOT EXISTS formex_dimensions (
|
||||
width_mm INTEGER NOT NULL,
|
||||
height_mm INTEGER NOT NULL,
|
||||
thickness_mm INTEGER NOT NULL,
|
||||
price_chf REAL,
|
||||
is_default INTEGER DEFAULT 0
|
||||
);
|
||||
|
||||
@@ -200,3 +201,16 @@ CREATE INDEX IF NOT EXISTS idx_blum_hardware_type ON blum_hardware(type);
|
||||
CREATE INDEX IF NOT EXISTS idx_handle_variants_style ON handle_variants(style);
|
||||
CREATE INDEX IF NOT EXISTS idx_hinge_variants_type ON hinge_variants(type);
|
||||
CREATE INDEX IF NOT EXISTS idx_element_colors_order ON element_colors(order_id);
|
||||
|
||||
-- Exports de plans/debitage enregistrés par commande
|
||||
CREATE TABLE IF NOT EXISTS plan_exports (
|
||||
id INTEGER PRIMARY KEY AUTOINCREMENT,
|
||||
order_id INTEGER NOT NULL REFERENCES orders(id) ON DELETE CASCADE,
|
||||
export_type TEXT NOT NULL,
|
||||
file_name TEXT NOT NULL,
|
||||
file_path TEXT NOT NULL,
|
||||
mime_type TEXT,
|
||||
created_at TEXT DEFAULT (datetime('now'))
|
||||
);
|
||||
|
||||
CREATE INDEX IF NOT EXISTS idx_plan_exports_order ON plan_exports(order_id);
|
||||
|
||||
Reference in New Issue
Block a user