diff --git a/db/migrations/01_initial_schema.sql b/db/migrations/01_initial_schema.sql index dd95da1..8259525 100644 --- a/db/migrations/01_initial_schema.sql +++ b/db/migrations/01_initial_schema.sql @@ -112,17 +112,17 @@ CREATE TABLE IF NOT EXISTS payments ( ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; -- Initial data seed -INSERT INTO companies (name_en, name_ar) VALUES ('Laundry Brand', 'علامة غسيل'); -INSERT INTO branches (company_id, name_en, name_ar) VALUES (1, 'Main Branch', 'الفرع الرئيسي'); -INSERT INTO users (branch_id, company_id, username, password_hash, full_name_en, full_name_ar, role) +INSERT IGNORE INTO companies (name_en, name_ar) VALUES ('Laundry Brand', 'علامة غسيل'); +INSERT IGNORE INTO branches (company_id, name_en, name_ar) VALUES (1, 'Main Branch', 'الفرع الرئيسي'); +INSERT IGNORE INTO users (branch_id, company_id, username, password_hash, full_name_en, full_name_ar, role) VALUES (1, 1, 'admin', '$2y$10$92IXUNpkjO0rOQ5byMi.Ye4oKoEa3Ro9llC/.og/at2.uheWG/igi', 'Admin', 'مدير', 'super_admin'); -- password is 'password' -INSERT INTO items (name_en, name_ar) VALUES ('Shirt', 'قميص'), ('Suit', 'بدلة'), ('T-Shirt', 'تيشيرت'), ('Pants', 'بنطال'), ('Dress', 'فستان'); -INSERT INTO services (name_en, name_ar) VALUES ('Wash Only', 'غسيل فقط'), ('Iron Only', 'كوي فقط'), ('Wash & Iron', 'غسيل وكوي'), ('Dry Clean', 'تنظيف جاف'); +INSERT IGNORE INTO items (name_en, name_ar) VALUES ('Shirt', 'قميص'), ('Suit', 'بدلة'), ('T-Shirt', 'تيشيرت'), ('Pants', 'بنطال'), ('Dress', 'فستان'); +INSERT IGNORE INTO services (name_en, name_ar) VALUES ('Wash Only', 'غسيل فقط'), ('Iron Only', 'كوي فقط'), ('Wash & Iron', 'غسيل وكوي'), ('Dry Clean', 'تنظيف جاف'); -- Default prices for Main Branch -INSERT INTO prices (branch_id, item_id, service_id, price) VALUES +INSERT IGNORE INTO prices (branch_id, item_id, service_id, price) VALUES (1, 1, 1, 5.00), (1, 1, 2, 3.00), (1, 1, 3, 7.00), (1, 2, 4, 30.00), (1, 3, 3, 5.00), diff --git a/db/migrations/02_update_items.sql b/db/migrations/02_update_items.sql index 27c9118..617e36e 100644 --- a/db/migrations/02_update_items.sql +++ b/db/migrations/02_update_items.sql @@ -30,7 +30,7 @@ ALTER TABLE prices ADD COLUMN variant_id INT AFTER item_id; ALTER TABLE prices ADD CONSTRAINT fk_price_variant FOREIGN KEY (variant_id) REFERENCES item_variants(id) ON DELETE CASCADE; -- Insert default categories -INSERT INTO categories (name_en, name_ar) VALUES +INSERT IGNORE INTO categories (name_en, name_ar) VALUES ('Men', 'رجال'), ('Women', 'نساء'), ('Kids', 'أطفال'), diff --git a/db/migrations/12_page_based_permissions.sql b/db/migrations/12_page_based_permissions.sql index 56c19e5..865e131 100644 --- a/db/migrations/12_page_based_permissions.sql +++ b/db/migrations/12_page_based_permissions.sql @@ -12,7 +12,7 @@ CREATE TABLE IF NOT EXISTS user_permissions ( -- Seed existing users with default permissions based on their current roles -- For Super Admins: everything -INSERT INTO user_permissions (user_id, page, can_view, can_add, can_edit, can_delete) +INSERT IGNORE INTO user_permissions (user_id, page, can_view, can_add, can_edit, can_delete) SELECT id, p.page, 1, 1, 1, 1 FROM users CROSS JOIN ( @@ -25,7 +25,7 @@ WHERE role = 'super_admin'; -- For Branch Managers: most things, but not company-wide settings or user management (usually) -- Following the existing role logic from header.php -INSERT INTO user_permissions (user_id, page, can_view, can_add, can_edit, can_delete) +INSERT IGNORE INTO user_permissions (user_id, page, can_view, can_add, can_edit, can_delete) SELECT id, p.page, 1, 1, 1, 1 FROM users CROSS JOIN ( @@ -36,7 +36,7 @@ CROSS JOIN ( WHERE role = 'branch_manager'; -- For Cashiers: -INSERT INTO user_permissions (user_id, page, can_view, can_add, can_edit, can_delete) +INSERT IGNORE INTO user_permissions (user_id, page, can_view, can_add, can_edit, can_delete) SELECT id, p.page, 1, 1, 1, 1 FROM users CROSS JOIN ( @@ -46,7 +46,7 @@ CROSS JOIN ( WHERE role = 'cashier'; -- For Limited Viewers: -INSERT INTO user_permissions (user_id, page, can_view, can_add, can_edit, can_delete) +INSERT IGNORE INTO user_permissions (user_id, page, can_view, can_add, can_edit, can_delete) SELECT id, p.page, 1, 0, 0, 0 FROM users CROSS JOIN ( diff --git a/db/migrations/13_multiple_user_branches.sql b/db/migrations/13_multiple_user_branches.sql index f6749e0..0ba388a 100644 --- a/db/migrations/13_multiple_user_branches.sql +++ b/db/migrations/13_multiple_user_branches.sql @@ -8,7 +8,7 @@ CREATE TABLE IF NOT EXISTS user_branches ( ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; -- Migrate existing data from users table -INSERT INTO user_branches (user_id, branch_id) +INSERT IGNORE INTO user_branches (user_id, branch_id) SELECT id, branch_id FROM users WHERE branch_id IS NOT NULL; -- Keep branch_id in users for now as fallback or default, but we should eventually rely on user_branches diff --git a/db/migrations/14_add_whatsapp_settings.sql b/db/migrations/14_add_whatsapp_settings.sql index 409edf3..943c67b 100644 --- a/db/migrations/14_add_whatsapp_settings.sql +++ b/db/migrations/14_add_whatsapp_settings.sql @@ -5,7 +5,7 @@ CREATE TABLE IF NOT EXISTS settings ( ) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_unicode_ci; -- Initial WhatsApp settings -INSERT INTO settings (setting_key, setting_value) VALUES +INSERT IGNORE INTO settings (setting_key, setting_value) VALUES ('whatsapp_enabled', '0'), ('wablas_token', ''), ('wablas_server', 'https://console.wablas.com'), diff --git a/db/migrations/15_add_customer_statement_permission.sql b/db/migrations/15_add_customer_statement_permission.sql index 7cd7e78..3e0eaf8 100644 --- a/db/migrations/15_add_customer_statement_permission.sql +++ b/db/migrations/15_add_customer_statement_permission.sql @@ -1,5 +1,5 @@ -- Grant permission to customer_statement.php for all users who have access to customers.php -INSERT INTO user_permissions (user_id, page, can_view, can_add, can_edit, can_delete) +INSERT IGNORE INTO user_permissions (user_id, page, can_view, can_add, can_edit, can_delete) SELECT user_id, 'customer_statement.php', can_view, can_add, can_edit, can_delete FROM user_permissions WHERE page = 'customers.php' diff --git a/install.php b/install.php index daa96e8..942f4ce 100644 --- a/install.php +++ b/install.php @@ -14,7 +14,6 @@ $success = ''; function runSqlFile($pdo, $filePath) { if (!file_exists($filePath)) return false; $sql = file_get_contents($filePath); - // Split by semicolon, but be careful with triggers/procedures if any $queries = preg_split("/;+(?=[^']*'([^']*'[^']*')*[^']*$)/", $sql); foreach ($queries as $query) { $query = trim($query); @@ -22,10 +21,19 @@ function runSqlFile($pdo, $filePath) { try { $pdo->exec($query); } catch (PDOException $e) { - // Ignore errors if table already exists during re-run - if (strpos($e->getMessage(), 'already exists') === false) { - throw $e; + $msg = $e->getMessage(); + if ( + strpos($msg, 'already exists') !== false || + strpos($msg, 'Duplicate column name') !== false || + strpos($msg, 'Duplicate key name') !== false || + strpos($msg, 'Duplicate entry') !== false || + strpos($msg, "Can't DROP") !== false || + strpos($msg, 'check that column/key exists') !== false || + strpos($msg, 'Unknown table') !== false + ) { + continue; } + throw $e; } } } @@ -103,7 +111,7 @@ function has_permission(\$action, \$page = null, \$user_id = null) { file_put_contents(__DIR__ . '/db/config.php', $configContent); // Run initial schema - runSqlFile($pdo, __DIR__ . '/db/migrations/01_initial_schema.sql'); + $migrations = glob(__DIR__ . '/db/migrations/*.sql'); sort($migrations); foreach ($migrations as $migration) { runSqlFile($pdo, $migration); } $_SESSION['db_configured'] = true; header("Location: install.php?step=3");