feat(manager): add Nexus Instance Manager for demo orchestration
- Complete Flask-based control panel for multi-tenant POS instances - Dashboard with global stats, system health, and recent demos - Demo provisioning in 1 click with auto-expiration tracking - Tenant management: activate/deactivate, reset data, delete - Health monitoring: PostgreSQL, Redis, disk, memory, systemd services - Migration orchestration UI for running schema updates across all tenants - JWT authentication with manager_users table - Dark theme SPA frontend with real-time search and actions - systemd service file included
This commit is contained in:
86
manager/scripts/init_manager.py
Normal file
86
manager/scripts/init_manager.py
Normal file
@@ -0,0 +1,86 @@
|
||||
#!/usr/bin/env python3
|
||||
"""Initialize Nexus Instance Manager: create admin tables and default user."""
|
||||
import os
|
||||
import sys
|
||||
import bcrypt
|
||||
import argparse
|
||||
|
||||
# Add manager to path
|
||||
MANAGER_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
|
||||
if MANAGER_DIR not in sys.path:
|
||||
sys.path.insert(0, MANAGER_DIR)
|
||||
|
||||
from services.tenant_service import get_master_conn
|
||||
|
||||
|
||||
def init_schema():
|
||||
"""Create manager_users table in master DB if not exists."""
|
||||
conn = get_master_conn()
|
||||
cur = conn.cursor()
|
||||
|
||||
cur.execute("""
|
||||
CREATE TABLE IF NOT EXISTS manager_users (
|
||||
id SERIAL PRIMARY KEY,
|
||||
email VARCHAR(200) UNIQUE NOT NULL,
|
||||
name VARCHAR(200) NOT NULL DEFAULT 'Admin',
|
||||
password_hash VARCHAR(200) NOT NULL,
|
||||
role VARCHAR(20) DEFAULT 'admin',
|
||||
is_active BOOLEAN DEFAULT TRUE,
|
||||
created_at TIMESTAMPTZ DEFAULT NOW()
|
||||
)
|
||||
""")
|
||||
|
||||
cur.execute("""
|
||||
CREATE TABLE IF NOT EXISTS manager_audit_log (
|
||||
id SERIAL PRIMARY KEY,
|
||||
user_email VARCHAR(200),
|
||||
action VARCHAR(100) NOT NULL,
|
||||
details JSONB,
|
||||
created_at TIMESTAMPTZ DEFAULT NOW()
|
||||
)
|
||||
""")
|
||||
|
||||
conn.commit()
|
||||
cur.close()
|
||||
conn.close()
|
||||
print("[OK] Manager schema initialized.")
|
||||
|
||||
|
||||
def create_admin(email, password, name="Admin"):
|
||||
"""Create or update admin user."""
|
||||
pwd_hash = bcrypt.hashpw(password.encode(), bcrypt.gensalt()).decode()
|
||||
|
||||
conn = get_master_conn()
|
||||
cur = conn.cursor()
|
||||
cur.execute("""
|
||||
INSERT INTO manager_users (email, name, password_hash, role)
|
||||
VALUES (%s, %s, %s, 'admin')
|
||||
ON CONFLICT (email) DO UPDATE SET
|
||||
password_hash = EXCLUDED.password_hash,
|
||||
name = EXCLUDED.name,
|
||||
is_active = TRUE
|
||||
""", (email.lower(), name, pwd_hash))
|
||||
conn.commit()
|
||||
cur.close()
|
||||
conn.close()
|
||||
print(f"[OK] Admin user '{email}' created/updated.")
|
||||
|
||||
|
||||
def main():
|
||||
parser = argparse.ArgumentParser(description="Initialize Nexus Manager")
|
||||
parser.add_argument("--email", default="admin@nexus.local", help="Admin email")
|
||||
parser.add_argument("--password", default="nexus2026", help="Admin password")
|
||||
parser.add_argument("--name", default="Super Admin", help="Admin display name")
|
||||
args = parser.parse_args()
|
||||
|
||||
print("Nexus Instance Manager — Initialization")
|
||||
print("=" * 40)
|
||||
init_schema()
|
||||
create_admin(args.email, args.password, args.name)
|
||||
print("=" * 40)
|
||||
print(f"Login: {args.email}")
|
||||
print(f"URL: http://manager-ip:5003")
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
main()
|
||||
Reference in New Issue
Block a user