diff options
| author | Yuval Adam <_@yuv.al> | 2025-07-18 15:24:15 +0200 |
|---|---|---|
| committer | Yuval Adam <_@yuv.al> | 2025-07-18 15:24:15 +0200 |
| commit | 257ad34dd8baf2c2e4b3621d2477c9fd265b709e (patch) | |
| tree | 0f683c9fed13fa6b85f86a67aa5e21385932e6eb /domain_manager.py | |
Initial stuff works
Diffstat (limited to 'domain_manager.py')
| -rwxr-xr-x | domain_manager.py | 213 |
1 files changed, 213 insertions, 0 deletions
diff --git a/domain_manager.py b/domain_manager.py new file mode 100755 index 0000000..808339c --- /dev/null +++ b/domain_manager.py @@ -0,0 +1,213 @@ +#!/usr/bin/env python3 + +import sys +from typing import Dict, Any, Optional +from config import Config +from namecheap_api import NamecheapAPI +from cloudflare_api import CloudflareAPI + +class DomainManager: + def __init__(self, config: Config, sandbox: bool = False): + self.config = config + self.sandbox = sandbox + self.namecheap = NamecheapAPI(config, sandbox=sandbox) + self.cloudflare = CloudflareAPI(config) + + def register_and_setup_domain(self, domain: str, + registrant_info: Optional[Dict[str, str]] = None, + setup_workers: bool = True, + dry_run: bool = False) -> Dict[str, Any]: + """ + Complete domain registration and setup workflow: + 1. Check domain availability + 2. Verify pricing and account balance + 3. Register domain (with user confirmation) + 4. Add domain to Cloudflare + 5. Update nameservers in Namecheap + 6. Set up basic DNS records + """ + result = { + 'domain': domain, + 'steps_completed': [], + 'errors': [] + } + + try: + # Step 1: Check domain availability + print(f"Checking availability for {domain}...") + if not self.namecheap.check_domain_availability(domain): + result['errors'].append(f"Domain {domain} is not available") + return result + + result['steps_completed'].append('availability_check') + print(f"✓ Domain {domain} is available") + + # Step 2: Check pricing and balance + print("Checking pricing and account balance...") + + try: + pricing = self.namecheap.get_domain_pricing(domain) + except Exception as e: + result['errors'].append(f"Failed to get domain pricing: {str(e)}") + return result + + try: + balance = self.namecheap.get_account_balance() + except Exception as e: + result['errors'].append(f"Failed to get account balance: {str(e)}") + return result + + if balance < pricing['register']: + result['errors'].append( + f"Insufficient balance. Required: ${pricing['register']:.2f}, " + f"Available: ${balance:.2f}" + ) + return result + + result['steps_completed'].append('pricing_check') + print(f"✓ Pricing: ${pricing['register']:.2f}, Balance: ${balance:.2f}") + + # Step 3: User confirmation with multiple safeguards + print(f"\n" + "="*50) + print(f"DOMAIN REGISTRATION CONFIRMATION") + print(f"="*50) + print(f"Domain: {domain}") + print(f"Registration Price: ${pricing['register']:.2f}") + print(f"Account Balance: ${balance:.2f}") + print(f"Remaining Balance: ${balance - pricing['register']:.2f}") + print(f"="*50) + + # Multiple confirmation steps to prevent accidents + print(f"\nWARNING: This will charge ${pricing['register']:.2f} to your account!") + first_confirm = input(f"Type 'REGISTER' to proceed with registration of {domain}: ").strip() + if first_confirm != 'REGISTER': + result['errors'].append("Registration cancelled by user") + return result + + second_confirm = input(f"Are you absolutely sure you want to register {domain} for ${pricing['register']:.2f}? (yes/no): ").lower().strip() + if second_confirm != 'yes': + result['errors'].append("Registration cancelled by user") + return result + + # Step 4: Register domain + if dry_run: + print(f"DRY RUN: Would register domain {domain} (skipping actual registration)") + result['steps_completed'].append('domain_registration_dry_run') + else: + print(f"Registering domain {domain}...") + if not self.namecheap.register_domain(domain, registrant_info=registrant_info): + result['errors'].append(f"Failed to register domain {domain}") + return result + result['steps_completed'].append('domain_registration') + + print(f"✓ Domain {domain} registered successfully") + + # Step 5: Add domain to Cloudflare + print(f"Adding {domain} to Cloudflare...") + zone_info = self.cloudflare.add_zone(domain) + zone_id = zone_info['id'] + + result['steps_completed'].append('cloudflare_zone_creation') + result['zone_id'] = zone_id + print(f"✓ Domain added to Cloudflare (Zone ID: {zone_id})") + + # Step 6: Get Cloudflare nameservers + print("Getting Cloudflare nameservers...") + nameservers = self.cloudflare.get_zone_nameservers(zone_id) + + result['nameservers'] = nameservers + print(f"✓ Cloudflare nameservers: {', '.join(nameservers)}") + + # Step 7: Update nameservers in Namecheap + print(f"Updating nameservers in Namecheap...") + if not self.namecheap.set_dns_servers(domain, nameservers): + result['errors'].append("Failed to update nameservers in Namecheap") + return result + + result['steps_completed'].append('nameserver_update') + print(f"✓ Nameservers updated in Namecheap") + + # Step 8: Set up basic DNS records + print("Setting up basic DNS records...") + dns_records = self.cloudflare.setup_basic_dns_records(zone_id, domain) + + result['dns_records'] = dns_records + result['steps_completed'].append('basic_dns_setup') + print(f"✓ Basic DNS records created") + + # Step 9: Set up worker subdomain if requested + if setup_workers: + print("Setting up worker subdomain...") + worker_record = self.cloudflare.create_worker_subdomain(zone_id, f"app.{domain}") + result['worker_record'] = worker_record + result['steps_completed'].append('worker_subdomain_setup') + print(f"✓ Worker subdomain app.{domain} created") + + result['success'] = True + print(f"\n🎉 Domain {domain} setup completed successfully!") + print(f"Zone ID: {zone_id}") + print(f"Nameservers: {', '.join(nameservers)}") + + return result + + except Exception as e: + result['errors'].append(f"Unexpected error: {str(e)}") + return result + + def setup_google_analytics_dns(self, domain: str) -> Dict[str, Any]: + """Set up DNS records for Google Analytics""" + try: + zone_info = self.cloudflare.get_zone_info(domain) + if not zone_info: + return {'error': f'Domain {domain} not found in Cloudflare'} + + records = self.cloudflare.setup_google_analytics_dns(zone_info['id'], domain) + return {'success': True, 'records': records} + + except Exception as e: + return {'error': str(e)} + +def main(): + if len(sys.argv) < 2: + print("Usage: python domain_manager.py <domain> [--dry-run] [--sandbox]") + sys.exit(1) + + domain = sys.argv[1] + dry_run = '--dry-run' in sys.argv + sandbox = '--sandbox' in sys.argv + + # Load configuration + config = Config.from_env() + + + # Validate required configuration + if not all([ + config.namecheap_api_key, + config.namecheap_api_user, + config.namecheap_username, + config.namecheap_client_ip, + config.cloudflare_api_token + ]): + print("Error: Missing required API credentials. Please check your .env file.") + sys.exit(1) + + # Initialize domain manager + manager = DomainManager(config, sandbox=sandbox) + + # Register and setup domain + if sandbox: + print("Running in SANDBOX mode - using Namecheap sandbox environment") + if dry_run: + print("Running in DRY RUN mode - no actual registration will occur") + result = manager.register_and_setup_domain(domain, dry_run=dry_run) + + if result.get('success'): + print(f"\nSuccess! Domain {domain} is ready for use.") + else: + print(f"\nErrors occurred:") + for error in result.get('errors', []): + print(f" - {error}") + sys.exit(1) + +if __name__ == "__main__": + main()
\ No newline at end of file |
