"""Initial domain schema""" from __future__ import annotations from alembic import op import sqlalchemy as sa # revision identifiers, used by Alembic. revision = "20251109_01" down_revision = None branch_labels = None depends_on = None mining_operation_type = sa.Enum( "open_pit", "underground", "in_situ_leach", "placer", "quarry", "mountaintop_removal", "other", name="miningoperationtype", ) scenario_status = sa.Enum( "draft", "active", "archived", name="scenariostatus", ) financial_category = sa.Enum( "capex", "opex", "revenue", "contingency", "other", name="financialcategory", ) cost_bucket = sa.Enum( "capital_initial", "capital_sustaining", "operating_fixed", "operating_variable", "maintenance", "reclamation", "royalties", "general_admin", name="costbucket", ) distribution_type = sa.Enum( "normal", "triangular", "uniform", "lognormal", "custom", name="distributiontype", ) stochastic_variable = sa.Enum( "ore_grade", "recovery_rate", "metal_price", "operating_cost", "capital_cost", "discount_rate", "throughput", name="stochasticvariable", ) resource_type = sa.Enum( "diesel", "electricity", "water", "explosives", "reagents", "labor", "equipment_hours", "tailings_capacity", name="resourcetype", ) def upgrade() -> None: bind = op.get_bind() mining_operation_type.create(bind, checkfirst=True) scenario_status.create(bind, checkfirst=True) financial_category.create(bind, checkfirst=True) cost_bucket.create(bind, checkfirst=True) distribution_type.create(bind, checkfirst=True) stochastic_variable.create(bind, checkfirst=True) resource_type.create(bind, checkfirst=True) op.create_table( "projects", sa.Column("id", sa.Integer(), nullable=False), sa.Column("name", sa.String(length=255), nullable=False), sa.Column("location", sa.String(length=255), nullable=True), sa.Column("operation_type", mining_operation_type, nullable=False), sa.Column("description", sa.Text(), nullable=True), sa.Column("created_at", sa.DateTime(timezone=True), server_default=sa.func.now(), nullable=False), sa.Column("updated_at", sa.DateTime(timezone=True), server_default=sa.func.now(), nullable=False), sa.PrimaryKeyConstraint("id"), sa.UniqueConstraint("name"), ) op.create_index(op.f("ix_projects_id"), "projects", ["id"], unique=False) op.create_table( "scenarios", sa.Column("id", sa.Integer(), nullable=False), sa.Column("project_id", sa.Integer(), nullable=False), sa.Column("name", sa.String(length=255), nullable=False), sa.Column("description", sa.Text(), nullable=True), sa.Column("status", scenario_status, nullable=False), sa.Column("start_date", sa.Date(), nullable=True), sa.Column("end_date", sa.Date(), nullable=True), sa.Column("discount_rate", sa.Numeric( precision=5, scale=2), nullable=True), sa.Column("currency", sa.String(length=3), nullable=True), sa.Column("primary_resource", resource_type, nullable=True), sa.Column("created_at", sa.DateTime(timezone=True), server_default=sa.func.now(), nullable=False), sa.Column("updated_at", sa.DateTime(timezone=True), server_default=sa.func.now(), nullable=False), sa.ForeignKeyConstraint( ["project_id"], ["projects.id"], ondelete="CASCADE"), sa.PrimaryKeyConstraint("id"), ) op.create_index(op.f("ix_scenarios_id"), "scenarios", ["id"], unique=False) op.create_index(op.f("ix_scenarios_project_id"), "scenarios", ["project_id"], unique=False) op.create_table( "financial_inputs", sa.Column("id", sa.Integer(), nullable=False), sa.Column("scenario_id", sa.Integer(), nullable=False), sa.Column("name", sa.String(length=255), nullable=False), sa.Column("category", financial_category, nullable=False), sa.Column("cost_bucket", cost_bucket, nullable=True), sa.Column("amount", sa.Numeric(precision=18, scale=2), nullable=False), sa.Column("currency", sa.String(length=3), nullable=True), sa.Column("effective_date", sa.Date(), nullable=True), sa.Column("notes", sa.Text(), nullable=True), sa.Column("created_at", sa.DateTime(timezone=True), server_default=sa.func.now(), nullable=False), sa.Column("updated_at", sa.DateTime(timezone=True), server_default=sa.func.now(), nullable=False), sa.ForeignKeyConstraint( ["scenario_id"], ["scenarios.id"], ondelete="CASCADE"), sa.PrimaryKeyConstraint("id"), ) op.create_index(op.f("ix_financial_inputs_id"), "financial_inputs", ["id"], unique=False) op.create_index(op.f("ix_financial_inputs_scenario_id"), "financial_inputs", ["scenario_id"], unique=False) op.create_table( "simulation_parameters", sa.Column("id", sa.Integer(), nullable=False), sa.Column("scenario_id", sa.Integer(), nullable=False), sa.Column("name", sa.String(length=255), nullable=False), sa.Column("distribution", distribution_type, nullable=False), sa.Column("variable", stochastic_variable, nullable=True), sa.Column("resource_type", resource_type, nullable=True), sa.Column("mean_value", sa.Numeric( precision=18, scale=4), nullable=True), sa.Column("standard_deviation", sa.Numeric( precision=18, scale=4), nullable=True), sa.Column("minimum_value", sa.Numeric( precision=18, scale=4), nullable=True), sa.Column("maximum_value", sa.Numeric( precision=18, scale=4), nullable=True), sa.Column("unit", sa.String(length=32), nullable=True), sa.Column("configuration", sa.JSON(), nullable=True), sa.Column("created_at", sa.DateTime(timezone=True), server_default=sa.func.now(), nullable=False), sa.Column("updated_at", sa.DateTime(timezone=True), server_default=sa.func.now(), nullable=False), sa.ForeignKeyConstraint( ["scenario_id"], ["scenarios.id"], ondelete="CASCADE"), sa.PrimaryKeyConstraint("id"), ) op.create_index(op.f("ix_simulation_parameters_id"), "simulation_parameters", ["id"], unique=False) op.create_index(op.f("ix_simulation_parameters_scenario_id"), "simulation_parameters", ["scenario_id"], unique=False) def downgrade() -> None: op.drop_index(op.f("ix_simulation_parameters_scenario_id"), table_name="simulation_parameters") op.drop_index(op.f("ix_simulation_parameters_id"), table_name="simulation_parameters") op.drop_table("simulation_parameters") op.drop_index(op.f("ix_financial_inputs_scenario_id"), table_name="financial_inputs") op.drop_index(op.f("ix_financial_inputs_id"), table_name="financial_inputs") op.drop_table("financial_inputs") op.drop_index(op.f("ix_scenarios_project_id"), table_name="scenarios") op.drop_index(op.f("ix_scenarios_id"), table_name="scenarios") op.drop_table("scenarios") op.drop_index(op.f("ix_projects_id"), table_name="projects") op.drop_table("projects") resource_type.drop(op.get_bind(), checkfirst=True) stochastic_variable.drop(op.get_bind(), checkfirst=True) distribution_type.drop(op.get_bind(), checkfirst=True) cost_bucket.drop(op.get_bind(), checkfirst=True) financial_category.drop(op.get_bind(), checkfirst=True) scenario_status.drop(op.get_bind(), checkfirst=True) mining_operation_type.drop(op.get_bind(), checkfirst=True)