- Added a new column `subscriptions_locked` to the `customers` table to manage subscription access. - Implemented a script to create new modules from a template, including updates to various files (module.json, README.md, router.py, views.py, and migration SQL). - Developed a script to import BMC Office subscriptions from an Excel file into the database, including error handling and statistics reporting. - Created a script to lookup and update missing CVR numbers using the CVR.dk API. - Implemented a script to relink Hub customers to e-conomic customer numbers based on name matching. - Developed scripts to sync CVR numbers from Simply-CRM and vTiger to the local customers database.
132 lines
3.9 KiB
Python
132 lines
3.9 KiB
Python
#!/usr/bin/env python3
|
|
"""
|
|
Sync CVR numbers from vTiger to local customers database
|
|
"""
|
|
import sys
|
|
import os
|
|
import asyncio
|
|
from dotenv import load_dotenv
|
|
|
|
# Load environment variables
|
|
load_dotenv()
|
|
|
|
# Override DATABASE_URL for local execution
|
|
if "postgres:5432" in os.getenv("DATABASE_URL", ""):
|
|
os.environ["DATABASE_URL"] = os.getenv("DATABASE_URL").replace("postgres:5432", "localhost:5433")
|
|
|
|
# Add parent directory to path
|
|
sys.path.insert(0, os.path.join(os.path.dirname(__file__), '..'))
|
|
|
|
from app.core.database import execute_query, execute_update, init_db
|
|
from app.services.vtiger_service import get_vtiger_service
|
|
|
|
|
|
async def sync_cvr_numbers():
|
|
"""Sync CVR numbers from vTiger Accounts to local customers"""
|
|
|
|
print("🔌 Forbinder til database...")
|
|
init_db()
|
|
|
|
print("🔌 Forbinder til vTiger...")
|
|
vtiger = get_vtiger_service()
|
|
|
|
# Test connection
|
|
if not await vtiger.test_connection():
|
|
print("❌ vTiger forbindelse fejlede")
|
|
return
|
|
|
|
# Get all customers with vtiger_id but no cvr_number
|
|
print("\n📊 Henter kunder uden CVR...")
|
|
customers = execute_query("""
|
|
SELECT id, name, vtiger_id, cvr_number
|
|
FROM customers
|
|
WHERE vtiger_id IS NOT NULL
|
|
AND (cvr_number IS NULL OR cvr_number = '')
|
|
ORDER BY name
|
|
""")
|
|
|
|
print(f"✅ Fundet {len(customers)} kunder uden CVR\n")
|
|
|
|
if len(customers) == 0:
|
|
print("✅ Alle kunder har allerede CVR numre!")
|
|
return
|
|
|
|
# Fetch all accounts from Simply-CRM (vTiger) with CVR
|
|
print("📥 Henter alle firmaer fra Simply-CRM (bmcnetworks.simply-crm.dk)...")
|
|
|
|
# Get all accounts in batches
|
|
all_accounts = []
|
|
batch_size = 100
|
|
total_fetched = 0
|
|
|
|
while True:
|
|
query = f"SELECT id, accountname, cf_accounts_cvr FROM Accounts LIMIT {batch_size} OFFSET {total_fetched};"
|
|
try:
|
|
batch = await vtiger.query(query)
|
|
except:
|
|
# If OFFSET fails, just get what we can
|
|
if total_fetched == 0:
|
|
query = "SELECT id, accountname, cf_accounts_cvr FROM Accounts LIMIT 10000;"
|
|
batch = await vtiger.query(query)
|
|
all_accounts.extend(batch)
|
|
break
|
|
|
|
if not batch or len(batch) == 0:
|
|
break
|
|
|
|
all_accounts.extend(batch)
|
|
total_fetched += len(batch)
|
|
print(f" ... hentet {total_fetched} firmaer")
|
|
|
|
if len(batch) < batch_size:
|
|
break
|
|
|
|
accounts = all_accounts
|
|
print(f"✅ Fundet {len(accounts)} firmaer i Simply-CRM")
|
|
|
|
# Filter to only those with CVR
|
|
accounts_with_cvr = {
|
|
acc['id']: acc['cf_accounts_cvr'].strip()
|
|
for acc in accounts
|
|
if acc.get('cf_accounts_cvr') and acc['cf_accounts_cvr'].strip()
|
|
}
|
|
|
|
print(f"✅ {len(accounts_with_cvr)} firmaer har CVR nummer i Simply-CRM\n")
|
|
|
|
# Match and update
|
|
updated = 0
|
|
skipped = 0
|
|
|
|
print("🔄 Opdaterer CVR numre...\n")
|
|
|
|
for customer in customers:
|
|
vtiger_id = customer['vtiger_id']
|
|
|
|
if vtiger_id in accounts_with_cvr:
|
|
cvr = accounts_with_cvr[vtiger_id]
|
|
|
|
# Clean CVR (remove spaces, dashes)
|
|
cvr_clean = cvr.replace(' ', '').replace('-', '')
|
|
|
|
# Update customer
|
|
execute_update(
|
|
"UPDATE customers SET cvr_number = %s WHERE id = %s",
|
|
(cvr_clean, customer['id'])
|
|
)
|
|
|
|
print(f" ✓ {customer['name']:<50} CVR: {cvr_clean}")
|
|
updated += 1
|
|
else:
|
|
skipped += 1
|
|
|
|
# Summary
|
|
print(f"\n{'='*60}")
|
|
print(f"✅ Opdatering færdig!")
|
|
print(f" Opdateret: {updated}")
|
|
print(f" Ikke fundet i vTiger: {skipped}")
|
|
print(f"{'='*60}\n")
|
|
|
|
|
|
if __name__ == "__main__":
|
|
asyncio.run(sync_cvr_numbers())
|