#!/usr/bin/env python3 """ Update TLD prices from Namecheap API with current exchange rate """ import os import math import requests import xml.etree.ElementTree as ET from datetime import datetime from dotenv import load_dotenv from db import get_connection, init_db load_dotenv() NS = {"nc": "http://api.namecheap.com/xml.response"} def get_exchange_rate() -> float: """Fetch current USD to KRW exchange rate""" resp = requests.get( "https://api.exchangerate-api.com/v4/latest/USD", timeout=30 ) resp.raise_for_status() return resp.json()["rates"]["KRW"] def get_namecheap_prices() -> dict[str, float]: """Fetch domain prices from Namecheap API""" params = { "ApiUser": os.getenv("NAMECHEAP_API_USER"), "ApiKey": os.getenv("NAMECHEAP_API_KEY"), "UserName": os.getenv("NAMECHEAP_USERNAME"), "ClientIp": os.getenv("NAMECHEAP_CLIENT_IP"), "Command": "namecheap.users.getPricing", "ProductType": "DOMAIN", "ProductCategory": "REGISTER", } resp = requests.get( "https://api.namecheap.com/xml.response", params=params, timeout=120 ) resp.raise_for_status() root = ET.fromstring(resp.text) prices = {} for product in root.findall(".//nc:Product", NS): tld = product.attrib.get("Name") for price in product.findall(".//nc:Price", NS): if price.attrib.get("Duration") == "1": prices[tld] = float(price.attrib.get("Price", 0)) break return prices VAT = 1.10 # 부가세 10% MARGIN = 1.03 # 마진 3% def to_krw_1000(usd: float, rate: float) -> int: """Convert USD to KRW with VAT + margin, rounded up to nearest 1000""" krw = usd * rate * VAT * MARGIN return math.ceil(krw / 1000) * 1000 def update_database(prices: dict[str, float], rate: float): """Update database with new prices""" conn = get_connection() now = datetime.now().isoformat() # Update exchange rate conn.execute( """ INSERT OR REPLACE INTO exchange_rates (currency, rate, updated_at) VALUES (?, ?, ?) """, ("KRW", rate, now) ) # Update TLD prices for tld, usd in prices.items(): krw = to_krw_1000(usd, rate) conn.execute( """ INSERT OR REPLACE INTO tld_prices (tld, usd, krw, updated_at) VALUES (?, ?, ?, ?) """, (tld, usd, krw, now) ) conn.commit() conn.close() def main(): print(f"[{datetime.now()}] Starting price update...") # Initialize DB if needed init_db() # Get exchange rate print("Fetching exchange rate...") rate = get_exchange_rate() print(f"USD/KRW: {rate:.2f}") # Get prices from Namecheap print("Fetching Namecheap prices...") prices = get_namecheap_prices() print(f"Got {len(prices)} TLD prices") # Update database print("Updating database...") update_database(prices, rate) print("Done!") # Show some popular TLDs popular = ["com", "net", "org", "io", "dev", "app", "me", "xyz", "co", "in"] print("\nPopular TLDs:") for tld in popular: if tld in prices: krw = to_krw_1000(prices[tld], rate) print(f" .{tld:6} ${prices[tld]:6.2f} → {krw:,}원") if __name__ == "__main__": main()