_scripts.py 3.0 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485868788899091
  1. import os
  2. import subprocess
  3. import sys
  4. from pathlib import Path
  5. from room_cal._utils import get_config
  6. def _data_home() -> Path:
  7. override = os.environ.get('ROOM_CAL_DATA_HOME')
  8. return Path(override) if override else Path.home() / '.local' / 'room_cal'
  9. def _ts_dir() -> Path:
  10. return Path(__file__).parent / 'typescript'
  11. def _npm_env() -> dict:
  12. dh = _data_home()
  13. env = os.environ.copy()
  14. env.setdefault('ROOM_CAL_DATA_HOME', str(dh))
  15. env.setdefault('PLAYWRIGHT_BROWSERS_PATH', str(dh / '.playwright-browsers'))
  16. api_url = get_config().api_url
  17. if api_url:
  18. env.setdefault('ROOM_CAL_API_URL', api_url)
  19. return env
  20. def _ensure_installed(ts_dir: Path) -> None:
  21. if not (ts_dir / 'node_modules').exists():
  22. print('=== npm install (service-api) ===')
  23. subprocess.run(['npm', 'install'], cwd=ts_dir, check=True)
  24. print()
  25. def refresh_booking_cookies() -> None:
  26. ts_dir = _ts_dir()
  27. _ensure_installed(ts_dir)
  28. try:
  29. subprocess.run(['npm', 'run', 'refresh-booking'], cwd=ts_dir, env=_npm_env(), check=True)
  30. except subprocess.CalledProcessError as e:
  31. from .types import ServiceAuthError
  32. raise ServiceAuthError(f'Booking.com credential refresh failed (exit {e.returncode})') from None
  33. def refresh_airbnb_cookies() -> None:
  34. ts_dir = _ts_dir()
  35. _ensure_installed(ts_dir)
  36. env = _npm_env()
  37. env['HEADLESS'] = '1'
  38. try:
  39. subprocess.run(['npm', 'run', 'refresh-airbnb'], cwd=ts_dir, env=env, check=True)
  40. except subprocess.CalledProcessError as e:
  41. from .types import ServiceAuthError
  42. raise ServiceAuthError(f'Airbnb session expired — re-run without HEADLESS to re-authenticate (exit {e.returncode})') from None
  43. def refresh_homestay_cookies() -> None:
  44. ts_dir = _ts_dir()
  45. _ensure_installed(ts_dir)
  46. env = _npm_env()
  47. try:
  48. subprocess.run(['npm', 'run', 'refresh-homestay'], cwd=ts_dir, env=env, check=True)
  49. except subprocess.CalledProcessError as e:
  50. from .types import ServiceAuthError
  51. raise ServiceAuthError(f'Homestay session expired — re-run without HEADLESS to re-authenticate (exit {e.returncode})') from None
  52. def trigger_booking_chat_auth() -> None:
  53. """Run booking-2fa; raises ServiceAuthError on failure. Safe to call from within the server."""
  54. ts_dir = _ts_dir()
  55. _ensure_installed(ts_dir)
  56. result = subprocess.run(['npm', 'run', 'booking-2fa'], cwd=ts_dir, env=_npm_env())
  57. if result.returncode != 0:
  58. from .types import ServiceAuthError
  59. raise ServiceAuthError(f'booking-2fa failed (exit {result.returncode}) — SMS gateway may not be configured')
  60. def _trigger_booking_chat_auth_cli() -> None:
  61. """CLI entry point for `uv run booking-2fa`."""
  62. ts_dir = _ts_dir()
  63. _ensure_installed(ts_dir)
  64. result = subprocess.run(['npm', 'run', 'booking-2fa', '--'] + sys.argv[1:], cwd=ts_dir, env=_npm_env())
  65. sys.exit(result.returncode)
  66. def refresh_cookies() -> None:
  67. ts_dir = _ts_dir()
  68. _ensure_installed(ts_dir)
  69. result = subprocess.run(['npm', 'run', 'refresh-all', '--'] + sys.argv[1:], cwd=ts_dir, env=_npm_env())
  70. sys.exit(result.returncode)