Skip to content

TaiNgo30/python-sync-app

Repository files navigation

Sync Python App (PySide6)

A desktop shell embedding a browser with two tabs (Odoo + MISA), a left sidebar for sync actions, logs panel, and an internal skeleton for MISA ↔ Odoo sync.

UI Overview

  • Two tabs open on startup:
    • Odoo: ODOO_BASE (default http://localhost:8069)
    • MISA: https://amisapp.misa.vn/login/
  • Sidebar options (mock):
    • "Sync Kho hàng" (Inventory) → runs a background diff job
    • "Sync Sản phẩm", "Sync Đối tác" placeholders
  • Bottom log area shows job lifecycle and results

Run

python -m venv .venv
. .venv\Scripts\Activate.ps1
pip install --upgrade pip
pip install -r requirements.txt
python run_app.py

Build EXE

./build_windows.ps1 -Clean
# Output: dist/SyncPythonApp.exe

Internal Structure (everything stays inside the app folder)

app/
  main.py                 # Qt entry
  ui/main_window.py       # Sidebar + tabs + logs
  widgets/browser_widget.py
  jobs/runner.py          # QThread-based background jobs
  sync/                   # Adapters & diff
    misa_adapter.py       # Export/parse skeleton (mock)
    odoo_adapter.py       # Import/export skeleton (mock)
    sync_service.py       # Diff by key utilities
  resources/              # (icons/assets placeholder)

Inventory Sync Flow (skeleton)

  • Trigger: click "Sync Kho hàng" in sidebar.
  • Background job (non-blocking):
    1. MisaAdapter.iter_inventory_records() yields source records (mocked now).
    2. OdooAdapter.get_existing_inventory() yields existing target records (mocked).
    3. diff_records(source, target, key="product_code") returns sets: to_create, to_update, to_remove.
    4. Display a small summary in the log area.
    5. Next step (to implement): call OdooAdapter.import_inventory(...) for creates/updates.

Async/Non-blocking Design

  • Uses JobRunner with QThread to avoid blocking the UI while parsing/converting large Excel files or performing comparisons.
  • Future work: parsing Excel (ClosedXML/openpyxl/pandas) and converting to Odoo CSV can run inside a JobRunner job and store intermediate files in an app-owned temp dir.

Next Steps for Real Sync

  • Implement real export from MISA to .xlsx and parse to normalized records.
  • Implement mapping to Odoo CSV columns; call Odoo import or RPC.
  • Add a Config page (inside the app) to manage credentials and mappings.
  • Persist app settings under an internal config directory (e.g., %LOCALAPPDATA%/SyncPythonApp).

Secure Middleware Flow

  • Sidebar action "Khoi tao ket noi an toan" runs key provisioning and the bootstrap handshake in a background job. Keys persist under app/resources/security/node_public.pem and app/resources/security/desktop_private.pem.
  • SecureSyncClient performs provisioning, encrypts {misa, hhwms} with RSA-OAEP(SHA-256), and signs canonical strings with Ed25519 before sending over HTTPS.
  • Every /api/** request is signed (X-Timestamp, X-Signature, X-Sign-Alg). The middleware validates signatures, decrypts the bootstrap payload once, and reuses cached tokens for outgoing MISA/Odoo calls. TLS remains mandatory (ALLOW_HTTP_DEV=true only for local development).
  • Middleware stores generated keys (RSA private/public, desktop public) under security_artifacts/ so restarts keep trusted materials.

Desktop Environment Variables

Variable Purpose
SYNC_MIDDLEWARE_BASE_URL HTTPS base URL of the Node middleware (e.g. https://localhost:3443).
ODOO_BASE Base URL of the Odoo/HHWH instance used across desktop flows (e.g. http://localhost:8069).
SYNC_BOOTSTRAP_FILE Path (relative to app/ or absolute) to the JSON file containing misa and hhwms bootstrap payloads.

The bootstrap file stores cookies as structured JSON (matching browser exports); the desktop app converts them to header strings when contacting the middleware.

Node Middleware Security Notes

  • New endpoints under /api: key provisioning (/keys/generate-node, /keys/generate-desktop) and secure bootstrap (/bootstrap).
  • All /api data routes (/customers, /quotations, etc.) now require signed GET requests; tokens are pulled from the bootstrap cache instead of .env when present.
  • TLS is enforced server-side; run behind a TLS terminator or configure HTTPS bindings. Use ALLOW_HTTP_DEV=true only during local development.

Module Isolation

Each sync runs in its own feature module under app/features/ so code and state do not interfere:

app/
  core/
    app_paths.py          # app-local data dirs
    selenium_driver.py    # persistent Chrome profile factory
    session_store.py      # cookies/tokens JSON store
  features/
    inventory_sync/
      service.py          # orchestrator for inventory
      misa/
        session.py        # access to MISA Chrome profile + cookies
        export.py         # (placeholder) selenium flow to export inventory
      odoo/
        importer.py       # (placeholder) import flow
    product_sync/
      __init__.py
    partner_sync/
      __init__.py
  • Selenium profiles are stored inside the app data dir: %LOCALAPPDATA%/SyncPythonApp/profiles/<site> so sessions/cookies persist across runs without touching outside folders.
  • Feature-specific working files go to %LOCALAPPDATA%/SyncPythonApp/features/<feature> and temp files to %LOCALAPPDATA%/SyncPythonApp/tmp/<feature>.

Running Inventory Diff (mock)

  • In the UI, click "📦 Sync Kho hàng". It runs features.inventory_sync.service.run_diff_only in a background thread and prints a summary in logs.
  • To connect to real MISA: implement the Selenium steps in features/inventory_sync/misa/export.py (after login, navigate and export), then parse and map to Odoo before import.

Product Sync (Export -> Convert -> Import)

  • Click "🧾 Sync Sản phẩm" in the sidebar.
  • Background steps:
    1. Export Excel từ MISA (Selenium + session lưu trong %LOCALAPPDATA%/SyncPythonApp/profiles/misa-product). Hiện tại mock tạo file để minh họa.
    2. Convert sang CSV định dạng Odoo (name, default_code, barcode, list_price, standard_price, uom_id/name).
    3. Import vào Odoo (stub đếm số dòng) — thay bằng RPC/CSV import thật khi có thông tin kết nối.
  • Files luôn nằm trong thư mục nội bộ:
    • MISA exports: %LOCALAPPDATA%/SyncPythonApp/features/product/misa_exports/
    • Odoo imports: %LOCALAPPDATA%/SyncPythonApp/features/product/odoo_imports/
  • Log hiển thị tiến trình ở panel phía dưới UI.

About

No description, website, or topics provided.

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published

Contributors 5