# sales_service ER map

Generated from SQLAlchemy metadata in `services.shared.sales_sql_models`.

## Summary
- `sales_leads`: 22 columns, 21 indexes, 0 foreign keys
- `sales_deals`: 32 columns, 21 indexes, 0 foreign keys
- `sales_communication_sessions`: 23 columns, 17 indexes, 0 foreign keys
- `sales_messages`: 16 columns, 14 indexes, 0 foreign keys
- `sales_calls`: 19 columns, 17 indexes, 0 foreign keys
- `sales_transcripts`: 10 columns, 6 indexes, 0 foreign keys
- `sales_offers`: 17 columns, 9 indexes, 0 foreign keys
- `sales_deal_conditions`: missing
- `sales_conditions`: 19 columns, 6 indexes, 0 foreign keys
- `sales_counterparties`: 18 columns, 8 indexes, 0 foreign keys
- `sales_documents`: 15 columns, 10 indexes, 0 foreign keys
- `sales_invoices`: 18 columns, 13 indexes, 0 foreign keys
- `sales_payments`: 16 columns, 10 indexes, 0 foreign keys
- `sales_stage_history`: 10 columns, 8 indexes, 0 foreign keys
- `sales_escalations`: 11 columns, 10 indexes, 0 foreign keys
- `sales_automation_tasks`: 12 columns, 9 indexes, 0 foreign keys
- `sales_notes`: 9 columns, 7 indexes, 0 foreign keys
- `sales_channel_switches`: 9 columns, 8 indexes, 0 foreign keys
- `sales_external_links`: 20 columns, 16 indexes, 0 foreign keys

## `sales_leads`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `lead_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `source_type` | `VARCHAR(64)` | no | no | no | yes | `` |
| `source_channel` | `VARCHAR(32)` | no | no | no | yes | `` |
| `source_campaign_id` | `VARCHAR(128)` | yes | no | no | yes | `` |
| `full_name` | `VARCHAR(256)` | no | no | no | yes | `` |
| `company_name` | `VARCHAR(256)` | yes | no | no | yes | `` |
| `phone` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `email` | `VARCHAR(256)` | yes | no | no | yes | `` |
| `messenger_handles_json` | `TEXT` | no | no | no | no | `{}` |
| `lead_temperature` | `VARCHAR(16)` | no | no | no | yes | `` |
| `lead_score` | `FLOAT` | no | no | no | yes | `50.0` |
| `customer_type` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `segment_type` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `initial_need_summary` | `TEXT` | yes | no | no | no | `` |
| `preferred_channel` | `VARCHAR(32)` | no | no | no | yes | `` |
| `assigned_agent_type` | `VARCHAR(32)` | no | no | no | yes | `` |
| `status` | `VARCHAR(32)` | no | no | no | yes | `` |
| `crm_customer_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_leads_phone_email`: `phone`, `email`
- `idx_sales_leads_tenant_status_score`: `tenant_id`, `status`, `lead_score`
- `ix_sales_leads_assigned_agent_type`: `assigned_agent_type`
- `ix_sales_leads_company_name`: `company_name`
- `ix_sales_leads_created_at`: `created_at`
- `ix_sales_leads_crm_customer_id`: `crm_customer_id`
- `ix_sales_leads_customer_type`: `customer_type`
- `ix_sales_leads_email`: `email`
- `ix_sales_leads_full_name`: `full_name`
- `ix_sales_leads_lead_id` unique: `lead_id`
- `ix_sales_leads_lead_score`: `lead_score`
- `ix_sales_leads_lead_temperature`: `lead_temperature`
- `ix_sales_leads_phone`: `phone`
- `ix_sales_leads_preferred_channel`: `preferred_channel`
- `ix_sales_leads_segment_type`: `segment_type`
- `ix_sales_leads_source_campaign_id`: `source_campaign_id`
- `ix_sales_leads_source_channel`: `source_channel`
- `ix_sales_leads_source_type`: `source_type`
- `ix_sales_leads_status`: `status`
- `ix_sales_leads_tenant_id`: `tenant_id`
- `ix_sales_leads_updated_at`: `updated_at`

## `sales_deals`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `deal_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `lead_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `customer_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `pipeline_id` | `VARCHAR(64)` | no | no | no | yes | `sales_default` |
| `stage_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `scenario_type` | `VARCHAR(64)` | no | no | no | yes | `` |
| `priority` | `INTEGER` | no | no | no | yes | `3` |
| `title` | `VARCHAR(512)` | no | no | no | no | `` |
| `need_summary` | `TEXT` | yes | no | no | no | `` |
| `product_context_json` | `TEXT` | no | no | no | no | `{}` |
| `estimated_amount` | `FLOAT` | yes | no | no | no | `` |
| `final_amount` | `FLOAT` | yes | no | no | no | `` |
| `currency` | `VARCHAR(16)` | no | no | no | no | `KZT` |
| `payment_model` | `VARCHAR(64)` | yes | no | no | no | `` |
| `document_required` | `BOOLEAN` | no | no | no | no | `True` |
| `payment_required` | `BOOLEAN` | no | no | no | no | `True` |
| `assigned_human_user_id` | `VARCHAR(128)` | yes | no | no | yes | `` |
| `assigned_ai_orchestrator_id` | `VARCHAR(128)` | yes | no | no | no | `` |
| `preferred_channel` | `VARCHAR(32)` | no | no | no | yes | `` |
| `current_channel` | `VARCHAR(32)` | no | no | no | yes | `` |
| `status` | `VARCHAR(32)` | no | no | no | yes | `active` |
| `won_reason` | `TEXT` | yes | no | no | no | `` |
| `lost_reason` | `TEXT` | yes | no | no | no | `` |
| `close_reason` | `TEXT` | yes | no | no | no | `` |
| `next_action_type` | `VARCHAR(128)` | yes | no | no | yes | `` |
| `next_action_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `last_contact_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `closed_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_deals_customer_channel`: `customer_id`, `current_channel`
- `idx_sales_deals_next_action`: `next_action_at`, `status`
- `idx_sales_deals_tenant_stage_status`: `tenant_id`, `stage_id`, `status`
- `ix_sales_deals_assigned_human_user_id`: `assigned_human_user_id`
- `ix_sales_deals_closed_at`: `closed_at`
- `ix_sales_deals_created_at`: `created_at`
- `ix_sales_deals_current_channel`: `current_channel`
- `ix_sales_deals_customer_id`: `customer_id`
- `ix_sales_deals_deal_id` unique: `deal_id`
- `ix_sales_deals_last_contact_at`: `last_contact_at`
- `ix_sales_deals_lead_id`: `lead_id`
- `ix_sales_deals_next_action_at`: `next_action_at`
- `ix_sales_deals_next_action_type`: `next_action_type`
- `ix_sales_deals_pipeline_id`: `pipeline_id`
- `ix_sales_deals_preferred_channel`: `preferred_channel`
- `ix_sales_deals_priority`: `priority`
- `ix_sales_deals_scenario_type`: `scenario_type`
- `ix_sales_deals_stage_id`: `stage_id`
- `ix_sales_deals_status`: `status`
- `ix_sales_deals_tenant_id`: `tenant_id`
- `ix_sales_deals_updated_at`: `updated_at`

## `sales_communication_sessions`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `communication_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `lead_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `customer_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `channel_type` | `VARCHAR(16)` | no | no | no | yes | `` |
| `direction` | `VARCHAR(16)` | no | no | no | yes | `` |
| `agent_type` | `VARCHAR(32)` | no | no | no | yes | `` |
| `started_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `ended_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `duration_sec` | `INTEGER` | yes | no | no | no | `` |
| `subject` | `VARCHAR(512)` | yes | no | no | no | `` |
| `status` | `VARCHAR(32)` | no | no | no | yes | `active` |
| `summary` | `TEXT` | yes | no | no | no | `` |
| `transcript_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `next_action_type` | `VARCHAR(128)` | yes | no | no | no | `` |
| `next_action_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `sentiment` | `VARCHAR(32)` | yes | no | no | no | `` |
| `result_code` | `VARCHAR(64)` | yes | no | no | no | `` |
| `metadata_json` | `TEXT` | no | no | no | no | `{}` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_comm_channel_status`: `channel_type`, `status`
- `idx_sales_comm_deal_started`: `deal_id`, `started_at`
- `ix_sales_communication_sessions_agent_type`: `agent_type`
- `ix_sales_communication_sessions_channel_type`: `channel_type`
- `ix_sales_communication_sessions_communication_id` unique: `communication_id`
- `ix_sales_communication_sessions_created_at`: `created_at`
- `ix_sales_communication_sessions_customer_id`: `customer_id`
- `ix_sales_communication_sessions_deal_id`: `deal_id`
- `ix_sales_communication_sessions_direction`: `direction`
- `ix_sales_communication_sessions_ended_at`: `ended_at`
- `ix_sales_communication_sessions_lead_id`: `lead_id`
- `ix_sales_communication_sessions_next_action_at`: `next_action_at`
- `ix_sales_communication_sessions_started_at`: `started_at`
- `ix_sales_communication_sessions_status`: `status`
- `ix_sales_communication_sessions_tenant_id`: `tenant_id`
- `ix_sales_communication_sessions_transcript_id`: `transcript_id`
- `ix_sales_communication_sessions_updated_at`: `updated_at`

## `sales_messages`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `message_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `communication_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `sender_type` | `VARCHAR(32)` | no | no | no | yes | `` |
| `sender_id` | `VARCHAR(128)` | yes | no | no | yes | `` |
| `channel_provider` | `VARCHAR(32)` | no | no | no | yes | `` |
| `external_message_id` | `VARCHAR(128)` | yes | no | no | yes | `` |
| `body` | `TEXT` | no | no | no | no | `` |
| `attachments_json` | `TEXT` | no | no | no | no | `[]` |
| `delivery_status` | `VARCHAR(32)` | yes | no | no | yes | `` |
| `read_status` | `VARCHAR(32)` | yes | no | no | yes | `` |
| `message_metadata_json` | `TEXT` | no | no | no | no | `{}` |
| `sent_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_messages_deal_sent`: `deal_id`, `sent_at`
- `idx_sales_messages_ext_id`: `channel_provider`, `external_message_id`
- `ix_sales_messages_channel_provider`: `channel_provider`
- `ix_sales_messages_communication_id`: `communication_id`
- `ix_sales_messages_created_at`: `created_at`
- `ix_sales_messages_deal_id`: `deal_id`
- `ix_sales_messages_delivery_status`: `delivery_status`
- `ix_sales_messages_external_message_id`: `external_message_id`
- `ix_sales_messages_message_id` unique: `message_id`
- `ix_sales_messages_read_status`: `read_status`
- `ix_sales_messages_sender_id`: `sender_id`
- `ix_sales_messages_sender_type`: `sender_type`
- `ix_sales_messages_sent_at`: `sent_at`
- `ix_sales_messages_tenant_id`: `tenant_id`

## `sales_calls`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `call_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `communication_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `phone_number` | `VARCHAR(64)` | no | no | no | yes | `` |
| `direction` | `VARCHAR(16)` | no | no | no | yes | `` |
| `provider` | `VARCHAR(64)` | no | no | no | yes | `` |
| `external_call_id` | `VARCHAR(128)` | yes | no | no | yes | `` |
| `recording_url` | `TEXT` | yes | no | no | no | `` |
| `transcript_status` | `VARCHAR(32)` | no | no | no | yes | `pending` |
| `transcript_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `call_status` | `VARCHAR(32)` | no | no | no | yes | `started` |
| `summary` | `TEXT` | yes | no | no | no | `` |
| `started_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `ended_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `duration_sec` | `INTEGER` | yes | no | no | no | `` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_calls_deal_started`: `deal_id`, `started_at`
- `idx_sales_calls_ext_provider`: `provider`, `external_call_id`
- `ix_sales_calls_call_id` unique: `call_id`
- `ix_sales_calls_call_status`: `call_status`
- `ix_sales_calls_communication_id`: `communication_id`
- `ix_sales_calls_created_at`: `created_at`
- `ix_sales_calls_deal_id`: `deal_id`
- `ix_sales_calls_direction`: `direction`
- `ix_sales_calls_ended_at`: `ended_at`
- `ix_sales_calls_external_call_id`: `external_call_id`
- `ix_sales_calls_phone_number`: `phone_number`
- `ix_sales_calls_provider`: `provider`
- `ix_sales_calls_started_at`: `started_at`
- `ix_sales_calls_tenant_id`: `tenant_id`
- `ix_sales_calls_transcript_id`: `transcript_id`
- `ix_sales_calls_transcript_status`: `transcript_status`
- `ix_sales_calls_updated_at`: `updated_at`

## `sales_transcripts`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `transcript_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `call_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `language` | `VARCHAR(16)` | no | no | no | yes | `ru` |
| `transcript_text` | `TEXT` | no | no | no | no | `` |
| `diarization_json` | `TEXT` | no | no | no | no | `{}` |
| `extracted_entities_json` | `TEXT` | no | no | no | no | `{}` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `ix_sales_transcripts_call_id`: `call_id`
- `ix_sales_transcripts_created_at`: `created_at`
- `ix_sales_transcripts_language`: `language`
- `ix_sales_transcripts_tenant_id`: `tenant_id`
- `ix_sales_transcripts_transcript_id` unique: `transcript_id`
- `ix_sales_transcripts_updated_at`: `updated_at`

## `sales_offers`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `offer_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `offer_type` | `VARCHAR(32)` | no | no | no | yes | `` |
| `title` | `VARCHAR(256)` | no | no | no | no | `` |
| `description` | `TEXT` | yes | no | no | no | `` |
| `line_items_json` | `TEXT` | no | no | no | no | `[]` |
| `pricing_json` | `TEXT` | no | no | no | no | `{}` |
| `total_amount` | `FLOAT` | no | no | no | no | `0` |
| `currency` | `VARCHAR(16)` | no | no | no | no | `KZT` |
| `validity_until` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `status` | `VARCHAR(32)` | no | no | no | yes | `draft` |
| `rendered_document_url` | `TEXT` | yes | no | no | no | `` |
| `created_by_type` | `VARCHAR(32)` | no | no | no | no | `text_ai` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_offers_deal_status`: `deal_id`, `status`
- `ix_sales_offers_created_at`: `created_at`
- `ix_sales_offers_deal_id`: `deal_id`
- `ix_sales_offers_offer_id` unique: `offer_id`
- `ix_sales_offers_offer_type`: `offer_type`
- `ix_sales_offers_status`: `status`
- `ix_sales_offers_tenant_id`: `tenant_id`
- `ix_sales_offers_updated_at`: `updated_at`
- `ix_sales_offers_validity_until`: `validity_until`

## `sales_deal_conditions`

Not present in SQLAlchemy metadata / migrations. Current implementation uses `sales_conditions` for deal conditions.

## `sales_conditions`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `condition_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `product_name` | `VARCHAR(256)` | yes | no | no | no | `` |
| `service_name` | `VARCHAR(256)` | yes | no | no | no | `` |
| `quantity` | `FLOAT` | yes | no | no | no | `` |
| `unit` | `VARCHAR(32)` | yes | no | no | no | `` |
| `delivery_mode` | `VARCHAR(64)` | yes | no | no | no | `` |
| `execution_date` | `VARCHAR(64)` | yes | no | no | no | `` |
| `start_date` | `VARCHAR(64)` | yes | no | no | no | `` |
| `end_date` | `VARCHAR(64)` | yes | no | no | no | `` |
| `payment_terms` | `TEXT` | yes | no | no | no | `` |
| `custom_terms_json` | `TEXT` | no | no | no | no | `{}` |
| `agreed_price` | `FLOAT` | yes | no | no | no | `` |
| `currency` | `VARCHAR(16)` | no | no | no | no | `KZT` |
| `confirmed_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `ix_sales_conditions_condition_id` unique: `condition_id`
- `ix_sales_conditions_confirmed_at`: `confirmed_at`
- `ix_sales_conditions_created_at`: `created_at`
- `ix_sales_conditions_deal_id`: `deal_id`
- `ix_sales_conditions_tenant_id`: `tenant_id`
- `ix_sales_conditions_updated_at`: `updated_at`

## `sales_counterparties`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `counterparty_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `customer_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `company_name` | `VARCHAR(256)` | yes | no | no | no | `` |
| `full_name` | `VARCHAR(256)` | yes | no | no | no | `` |
| `bin_iin` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `address` | `TEXT` | yes | no | no | no | `` |
| `bank_details_json` | `TEXT` | no | no | no | no | `{}` |
| `signer_name` | `VARCHAR(256)` | yes | no | no | no | `` |
| `signer_role` | `VARCHAR(128)` | yes | no | no | no | `` |
| `signer_basis` | `VARCHAR(256)` | yes | no | no | no | `` |
| `email_for_docs` | `VARCHAR(256)` | yes | no | no | no | `` |
| `phone_for_docs` | `VARCHAR(64)` | yes | no | no | no | `` |
| `completeness_status` | `VARCHAR(32)` | no | no | no | yes | `draft` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `ix_sales_counterparties_bin_iin`: `bin_iin`
- `ix_sales_counterparties_completeness_status`: `completeness_status`
- `ix_sales_counterparties_counterparty_id` unique: `counterparty_id`
- `ix_sales_counterparties_created_at`: `created_at`
- `ix_sales_counterparties_customer_id`: `customer_id`
- `ix_sales_counterparties_deal_id` unique: `deal_id`
- `ix_sales_counterparties_tenant_id`: `tenant_id`
- `ix_sales_counterparties_updated_at`: `updated_at`

## `sales_documents`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `document_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `customer_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `document_type` | `VARCHAR(64)` | no | no | no | yes | `` |
| `template_id` | `VARCHAR(128)` | yes | no | no | no | `` |
| `version` | `INTEGER` | no | no | no | no | `1` |
| `status` | `VARCHAR(32)` | no | no | no | yes | `draft` |
| `file_url` | `TEXT` | yes | no | no | no | `` |
| `rendered_payload_json` | `TEXT` | no | no | no | no | `{}` |
| `external_sign_provider_id` | `VARCHAR(128)` | yes | no | no | no | `` |
| `signed_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_documents_deal_status`: `deal_id`, `status`
- `ix_sales_documents_created_at`: `created_at`
- `ix_sales_documents_customer_id`: `customer_id`
- `ix_sales_documents_deal_id`: `deal_id`
- `ix_sales_documents_document_id` unique: `document_id`
- `ix_sales_documents_document_type`: `document_type`
- `ix_sales_documents_signed_at`: `signed_at`
- `ix_sales_documents_status`: `status`
- `ix_sales_documents_tenant_id`: `tenant_id`
- `ix_sales_documents_updated_at`: `updated_at`

## `sales_invoices`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `invoice_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `customer_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `invoice_number` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `basis_document_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `amount` | `FLOAT` | no | no | no | no | `0` |
| `currency` | `VARCHAR(16)` | no | no | no | no | `KZT` |
| `due_date` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `status` | `VARCHAR(32)` | no | no | no | yes | `draft` |
| `payment_link` | `TEXT` | yes | no | no | no | `` |
| `line_items_json` | `TEXT` | no | no | no | no | `[]` |
| `metadata_json` | `TEXT` | no | no | no | no | `{}` |
| `issued_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `paid_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_invoices_deal_status_due`: `deal_id`, `status`, `due_date`
- `ix_sales_invoices_basis_document_id`: `basis_document_id`
- `ix_sales_invoices_created_at`: `created_at`
- `ix_sales_invoices_customer_id`: `customer_id`
- `ix_sales_invoices_deal_id`: `deal_id`
- `ix_sales_invoices_due_date`: `due_date`
- `ix_sales_invoices_invoice_id` unique: `invoice_id`
- `ix_sales_invoices_invoice_number` unique: `invoice_number`
- `ix_sales_invoices_issued_at`: `issued_at`
- `ix_sales_invoices_paid_at`: `paid_at`
- `ix_sales_invoices_status`: `status`
- `ix_sales_invoices_tenant_id`: `tenant_id`
- `ix_sales_invoices_updated_at`: `updated_at`

## `sales_payments`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `payment_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `invoice_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `payment_provider` | `VARCHAR(64)` | yes | no | no | no | `` |
| `external_payment_id` | `VARCHAR(128)` | yes | no | no | yes | `` |
| `amount` | `FLOAT` | no | no | no | no | `0` |
| `currency` | `VARCHAR(16)` | no | no | no | no | `KZT` |
| `status` | `VARCHAR(32)` | no | no | no | yes | `pending` |
| `paid_at` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `payment_method` | `VARCHAR(64)` | yes | no | no | no | `` |
| `failure_reason` | `TEXT` | yes | no | no | no | `` |
| `metadata_json` | `TEXT` | no | no | no | no | `{}` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_payments_deal_status`: `deal_id`, `status`
- `ix_sales_payments_created_at`: `created_at`
- `ix_sales_payments_deal_id`: `deal_id`
- `ix_sales_payments_external_payment_id`: `external_payment_id`
- `ix_sales_payments_invoice_id`: `invoice_id`
- `ix_sales_payments_paid_at`: `paid_at`
- `ix_sales_payments_payment_id` unique: `payment_id`
- `ix_sales_payments_status`: `status`
- `ix_sales_payments_tenant_id`: `tenant_id`
- `ix_sales_payments_updated_at`: `updated_at`

## `sales_stage_history`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `history_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `from_stage_id` | `VARCHAR(64)` | yes | no | no | no | `` |
| `to_stage_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `changed_by_type` | `VARCHAR(32)` | no | no | no | yes | `` |
| `changed_by_id` | `VARCHAR(128)` | yes | no | no | yes | `` |
| `reason` | `TEXT` | yes | no | no | no | `` |
| `changed_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_stage_history_deal_changed`: `deal_id`, `changed_at`
- `ix_sales_stage_history_changed_at`: `changed_at`
- `ix_sales_stage_history_changed_by_id`: `changed_by_id`
- `ix_sales_stage_history_changed_by_type`: `changed_by_type`
- `ix_sales_stage_history_deal_id`: `deal_id`
- `ix_sales_stage_history_history_id` unique: `history_id`
- `ix_sales_stage_history_tenant_id`: `tenant_id`
- `ix_sales_stage_history_to_stage_id`: `to_stage_id`

## `sales_escalations`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `escalation_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `escalation_type` | `VARCHAR(64)` | no | no | no | yes | `` |
| `reason` | `TEXT` | no | no | no | no | `` |
| `severity` | `VARCHAR(16)` | no | no | no | yes | `` |
| `status` | `VARCHAR(32)` | no | no | no | yes | `open` |
| `assigned_to_user_id` | `VARCHAR(128)` | yes | no | no | yes | `` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `resolved_at` | `VARCHAR(64)` | yes | no | no | yes | `` |

Indexes:
- `idx_sales_escalations_deal_status`: `deal_id`, `status`
- `ix_sales_escalations_assigned_to_user_id`: `assigned_to_user_id`
- `ix_sales_escalations_created_at`: `created_at`
- `ix_sales_escalations_deal_id`: `deal_id`
- `ix_sales_escalations_escalation_id` unique: `escalation_id`
- `ix_sales_escalations_escalation_type`: `escalation_type`
- `ix_sales_escalations_resolved_at`: `resolved_at`
- `ix_sales_escalations_severity`: `severity`
- `ix_sales_escalations_status`: `status`
- `ix_sales_escalations_tenant_id`: `tenant_id`

## `sales_automation_tasks`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `task_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `task_type` | `VARCHAR(64)` | no | no | no | yes | `` |
| `payload_json` | `TEXT` | no | no | no | no | `{}` |
| `run_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `status` | `VARCHAR(32)` | no | no | no | yes | `pending` |
| `retry_count` | `INTEGER` | no | no | no | no | `0` |
| `last_error` | `TEXT` | yes | no | no | no | `` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_tasks_run_status`: `run_at`, `status`
- `ix_sales_automation_tasks_created_at`: `created_at`
- `ix_sales_automation_tasks_deal_id`: `deal_id`
- `ix_sales_automation_tasks_run_at`: `run_at`
- `ix_sales_automation_tasks_status`: `status`
- `ix_sales_automation_tasks_task_id` unique: `task_id`
- `ix_sales_automation_tasks_task_type`: `task_type`
- `ix_sales_automation_tasks_tenant_id`: `tenant_id`
- `ix_sales_automation_tasks_updated_at`: `updated_at`

## `sales_notes`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `note_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `author_type` | `VARCHAR(32)` | no | no | no | yes | `` |
| `author_id` | `VARCHAR(128)` | yes | no | no | yes | `` |
| `note_type` | `VARCHAR(64)` | no | no | no | yes | `` |
| `content` | `TEXT` | no | no | no | no | `` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `ix_sales_notes_author_id`: `author_id`
- `ix_sales_notes_author_type`: `author_type`
- `ix_sales_notes_created_at`: `created_at`
- `ix_sales_notes_deal_id`: `deal_id`
- `ix_sales_notes_note_id` unique: `note_id`
- `ix_sales_notes_note_type`: `note_type`
- `ix_sales_notes_tenant_id`: `tenant_id`

## `sales_channel_switches`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `switch_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `communication_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `from_channel` | `VARCHAR(32)` | no | no | no | yes | `` |
| `to_channel` | `VARCHAR(32)` | no | no | no | yes | `` |
| `reason_for_channel_switch` | `TEXT` | no | no | no | no | `` |
| `switched_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_channel_switches_deal_switched`: `deal_id`, `switched_at`
- `ix_sales_channel_switches_communication_id`: `communication_id`
- `ix_sales_channel_switches_deal_id`: `deal_id`
- `ix_sales_channel_switches_from_channel`: `from_channel`
- `ix_sales_channel_switches_switch_id` unique: `switch_id`
- `ix_sales_channel_switches_switched_at`: `switched_at`
- `ix_sales_channel_switches_tenant_id`: `tenant_id`
- `ix_sales_channel_switches_to_channel`: `to_channel`

## `sales_external_links`

Physical foreign keys: none. Relations are stored as string ids and enforced only by service code.

| Column | Type | Null | PK | Unique | Indexed | Default |
|---|---|---:|---:|---:|---:|---|
| `id` | `INTEGER` | no | yes | no | no | `` |
| `link_id` | `VARCHAR(64)` | no | no | yes | yes | `` |
| `tenant_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `deal_id` | `VARCHAR(64)` | no | no | no | yes | `` |
| `communication_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `sales_call_id` | `VARCHAR(64)` | yes | no | no | yes | `` |
| `channel_provider` | `VARCHAR(32)` | no | no | no | yes | `` |
| `external_thread_id` | `VARCHAR(128)` | yes | no | no | no | `` |
| `external_chat_id` | `VARCHAR(128)` | yes | no | no | no | `` |
| `external_call_id` | `VARCHAR(128)` | yes | no | no | no | `` |
| `voice_session_id` | `VARCHAR(64)` | yes | no | no | no | `` |
| `ai_session_id` | `VARCHAR(64)` | yes | no | no | no | `` |
| `interaction_id` | `VARCHAR(64)` | yes | no | no | no | `` |
| `customer_id` | `VARCHAR(64)` | yes | no | no | no | `` |
| `phone_number` | `VARCHAR(64)` | yes | no | no | no | `` |
| `external_status` | `VARCHAR(32)` | yes | no | no | yes | `` |
| `link_metadata_json` | `TEXT` | no | no | no | no | `{}` |
| `created_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `updated_at` | `VARCHAR(64)` | no | no | no | yes | `` |
| `last_sync_at` | `VARCHAR(64)` | no | no | no | yes | `` |

Indexes:
- `idx_sales_external_links_customer_phone`: `customer_id`, `phone_number`
- `idx_sales_external_links_deal_sync`: `deal_id`, `last_sync_at`
- `idx_sales_external_links_external_call`: `external_call_id`
- `idx_sales_external_links_interaction`: `interaction_id`
- `idx_sales_external_links_thread`: `external_thread_id`
- `idx_sales_external_links_voice_session`: `voice_session_id`
- `ix_sales_external_links_channel_provider`: `channel_provider`
- `ix_sales_external_links_communication_id`: `communication_id`
- `ix_sales_external_links_created_at`: `created_at`
- `ix_sales_external_links_deal_id`: `deal_id`
- `ix_sales_external_links_external_status`: `external_status`
- `ix_sales_external_links_last_sync_at`: `last_sync_at`
- `ix_sales_external_links_link_id` unique: `link_id`
- `ix_sales_external_links_sales_call_id`: `sales_call_id`
- `ix_sales_external_links_tenant_id`: `tenant_id`
- `ix_sales_external_links_updated_at`: `updated_at`
