canister-operator-full-export.yml
yaml
sha256:65ccb454656ea5acdea0a10e559b78bcde1eb6ff753ecc2911bc99d1c3d7cadd
feat(calendar): enforce agent context tiers in retrieval AP…
Human
minor
⚠ breaking
1 day ago
| 1 | # Daily full logical export: all hub user ids + per-user notes/proposals (canister stays up). |
| 2 | # Requires: deployed hub WASM with operator export + secret set via admin_set_operator_export_secret. |
| 3 | # Secrets: KNOWTATION_OPERATOR_EXPORT_KEY (matches canister); URL optional (defaults from canister_ids.json). |
| 4 | name: Operator full hub export |
| 5 | |
| 6 | on: |
| 7 | schedule: |
| 8 | - cron: '30 7 * * *' |
| 9 | workflow_dispatch: |
| 10 | |
| 11 | permissions: |
| 12 | contents: read |
| 13 | |
| 14 | jobs: |
| 15 | export: |
| 16 | runs-on: ubuntu-latest |
| 17 | steps: |
| 18 | - uses: actions/checkout@v4 |
| 19 | |
| 20 | - name: Install dependencies |
| 21 | run: npm ci |
| 22 | |
| 23 | - name: Verify operator export secret |
| 24 | env: |
| 25 | KNOWTATION_OPERATOR_EXPORT_KEY: ${{ secrets.KNOWTATION_OPERATOR_EXPORT_KEY || vars.KNOWTATION_OPERATOR_EXPORT_KEY }} |
| 26 | run: | |
| 27 | python3 << 'PY' |
| 28 | import os |
| 29 | k = (os.environ.get("KNOWTATION_OPERATOR_EXPORT_KEY") or "").strip() |
| 30 | if not k: |
| 31 | print("::error::KNOWTATION_OPERATOR_EXPORT_KEY is missing or whitespace-only. Add Actions secret or variable.") |
| 32 | raise SystemExit(1) |
| 33 | PY |
| 34 | echo "KNOWTATION_OPERATOR_EXPORT_KEY is set (value not shown)." |
| 35 | |
| 36 | - name: Probe operator export (HTTP status only) |
| 37 | env: |
| 38 | KNOWTATION_OPERATOR_EXPORT_URL: ${{ secrets.KNOWTATION_OPERATOR_EXPORT_URL || vars.KNOWTATION_OPERATOR_EXPORT_URL }} |
| 39 | KNOWTATION_OPERATOR_EXPORT_KEY: ${{ secrets.KNOWTATION_OPERATOR_EXPORT_KEY || vars.KNOWTATION_OPERATOR_EXPORT_KEY }} |
| 40 | run: | |
| 41 | set -e |
| 42 | ID="$(python3 -c "import json; print(json.load(open('hub/icp/canister_ids.json'))['hub']['ic'])")" |
| 43 | BASE="$(python3 -c "import os; u=(os.environ.get('KNOWTATION_OPERATOR_EXPORT_URL') or '').strip().rstrip('/'); print(u)")" |
| 44 | if [ -z "$BASE" ]; then |
| 45 | BASE="https://${ID}.raw.icp0.io" |
| 46 | echo "KNOWTATION_OPERATOR_EXPORT_URL unset; using ${BASE} from canister_ids.json" |
| 47 | fi |
| 48 | echo "Probe base URL: ${BASE}" |
| 49 | code="$(curl -sS -o /tmp/op-export-body -w '%{http_code}' \ |
| 50 | -H "X-Operator-Export-Key: ${KNOWTATION_OPERATOR_EXPORT_KEY}" \ |
| 51 | "${BASE}/api/v1/operator/export?limit=1")" |
| 52 | echo "GET /api/v1/operator/export?limit=1 → HTTP ${code}" |
| 53 | head -c 300 /tmp/op-export-body || true |
| 54 | echo "" |
| 55 | if [ "$code" != "200" ]; then |
| 56 | echo "::error::Operator export returned HTTP ${code}. 401 = GitHub KNOWTATION_OPERATOR_EXPORT_KEY does not match admin_set_operator_export_secret. 503 = secret not set on canister." |
| 57 | exit 1 |
| 58 | fi |
| 59 | |
| 60 | - name: Full operator export |
| 61 | env: |
| 62 | KNOWTATION_OPERATOR_EXPORT_URL: ${{ secrets.KNOWTATION_OPERATOR_EXPORT_URL || vars.KNOWTATION_OPERATOR_EXPORT_URL }} |
| 63 | KNOWTATION_OPERATOR_EXPORT_KEY: ${{ secrets.KNOWTATION_OPERATOR_EXPORT_KEY || vars.KNOWTATION_OPERATOR_EXPORT_KEY }} |
| 64 | KNOWTATION_CANISTER_BACKUP_ENCRYPT_KEY_HEX: ${{ secrets.KNOWTATION_CANISTER_BACKUP_ENCRYPT_KEY_HEX || vars.KNOWTATION_CANISTER_BACKUP_ENCRYPT_KEY_HEX }} |
| 65 | KNOWTATION_CANISTER_BACKUP_S3_BUCKET: ${{ secrets.KNOWTATION_CANISTER_BACKUP_S3_BUCKET || vars.KNOWTATION_CANISTER_BACKUP_S3_BUCKET }} |
| 66 | KNOWTATION_CANISTER_BACKUP_S3_PREFIX: ${{ secrets.KNOWTATION_CANISTER_BACKUP_S3_PREFIX || vars.KNOWTATION_CANISTER_BACKUP_S3_PREFIX }} |
| 67 | AWS_ACCESS_KEY_ID: ${{ secrets.AWS_ACCESS_KEY_ID || vars.AWS_ACCESS_KEY_ID }} |
| 68 | AWS_SECRET_ACCESS_KEY: ${{ secrets.AWS_SECRET_ACCESS_KEY || vars.AWS_SECRET_ACCESS_KEY }} |
| 69 | AWS_REGION: ${{ secrets.AWS_REGION || vars.AWS_REGION }} |
| 70 | run: node scripts/canister-operator-full-export.mjs |
| 71 | |
| 72 | - name: Debug on failure (backup files and hub URL resolution) |
| 73 | if: failure() |
| 74 | env: |
| 75 | KNOWTATION_OPERATOR_EXPORT_URL: ${{ secrets.KNOWTATION_OPERATOR_EXPORT_URL || vars.KNOWTATION_OPERATOR_EXPORT_URL }} |
| 76 | KNOWTATION_CANISTER_URL: ${{ secrets.KNOWTATION_CANISTER_URL || vars.KNOWTATION_CANISTER_URL }} |
| 77 | KNOWTATION_CANISTER_BACKUP_URL: ${{ secrets.KNOWTATION_CANISTER_BACKUP_URL || vars.KNOWTATION_CANISTER_BACKUP_URL }} |
| 78 | run: | |
| 79 | echo "=== backups/ (if any) ===" |
| 80 | ls -la backups 2>/dev/null || echo "(no backups directory)" |
| 81 | find . -maxdepth 4 -name 'operator-full-export*' -print 2>/dev/null || true |
| 82 | echo "=== URL env (values may be empty) ===" |
| 83 | echo "KNOWTATION_OPERATOR_EXPORT_URL length: ${#KNOWTATION_OPERATOR_EXPORT_URL}" |
| 84 | echo "KNOWTATION_CANISTER_URL length: ${#KNOWTATION_CANISTER_URL}" |
| 85 | echo "KNOWTATION_CANISTER_BACKUP_URL length: ${#KNOWTATION_CANISTER_BACKUP_URL}" |
| 86 | echo "(Script resolves base URL as: OPERATOR_EXPORT_URL, then CANISTER_URL, then CANISTER_BACKUP_URL, then canister_ids.)" |
| 87 | |
| 88 | - name: Upload export artifact |
| 89 | if: success() |
| 90 | uses: actions/upload-artifact@v4 |
| 91 | with: |
| 92 | name: operator-full-export-${{ github.run_id }} |
| 93 | path: backups/operator-full-export-* |
| 94 | retention-days: 90 |
| 95 | if-no-files-found: error |
File History
2 commits
sha256:65ccb454656ea5acdea0a10e559b78bcde1eb6ff753ecc2911bc99d1c3d7cadd
feat(calendar): enforce agent context tiers in retrieval AP…
Human
minor
⚠
1 day ago
sha256:9103f98c89257ed2b01c237cea895dabb3e85ea337dccb1161c175e4422355b6
docs: accept Calendar Events v0 spec with Phase 0 security …
Human
2 days ago