-
Notifications
You must be signed in to change notification settings - Fork 0
Update deploy workflow and add VSCode/Neovim docs #5
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
base: Main
Are you sure you want to change the base?
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||
|---|---|---|---|---|---|---|
|
|
@@ -2,7 +2,7 @@ name: Deploy | |||||
|
|
||||||
| on: | ||||||
| push: | ||||||
| branches: [ "main" ] | ||||||
| branches: [ "main", "Main" ] | ||||||
| workflow_dispatch: | ||||||
| inputs: | ||||||
| dry_run: | ||||||
|
|
@@ -35,21 +35,21 @@ jobs: | |||||
| - name: Sync secrets from 1Password (SA preferred, Connect fallback) | ||||||
| env: | ||||||
| # Option 2: Service Account (preferred) | ||||||
| OP_SERVICE_ACCOUNT_TOKEN: $ secrets.OP_SERVICE_ACCOUNT_TOKEN | ||||||
| OP_SERVICE_ACCOUNT_TOKEN: ${{ secrets.OP_SERVICE_ACCOUNT_TOKEN }} | ||||||
| # Option 1: Connect server (fallback) | ||||||
| OP_CONNECT_HOST: $ secrets.OP_CONNECT_HOST | ||||||
| OP_CONNECT_TOKEN: $ secrets.OP_CONNECT_TOKEN | ||||||
| OP_CONNECT_HOST: ${{ secrets.OP_CONNECT_HOST }} | ||||||
| OP_CONNECT_TOKEN: ${{ secrets.OP_CONNECT_TOKEN }} | ||||||
| # Map selection (auto: staging branch -> staging map) | ||||||
| SECRETS_MAP: $ github.ref_name == 'staging' && '[secrets.map](http://secrets.map).staging.json' || '[secrets.map](http://secrets.map).json' | ||||||
| SECRETS_MAP: ${{ github.ref_name == 'staging' && 'secrets.map.staging.json' || 'secrets.map.json' }} | ||||||
| # DRY_RUN from workflow input | ||||||
| DRY_RUN: $ github.event.inputs.dry_run | ||||||
| DRY_RUN: ${{ github.event_name == 'workflow_dispatch' && github.event.inputs.dry_run || 'false' }} | ||||||
| run: | | ||||||
| sudo apt-get update && sudo apt-get install -y jq | ||||||
| bash scripts/[sync-secrets.sh](http://sync-secrets.sh) | ||||||
| bash scripts/sync-secrets.sh | ||||||
|
|
||||||
| - name: Deploy (Cloudflare Workers) | ||||||
| if: $ github.event.inputs.dry_run != 'true' && github.event.inputs.dry_run != '1' | ||||||
| if: ${{ !(github.event_name == 'workflow_dispatch' && (github.event.inputs.dry_run == 'true' || github.event.inputs.dry_run == '1')) }} | ||||||
|
||||||
| if: ${{ !(github.event_name == 'workflow_dispatch' && (github.event.inputs.dry_run == 'true' || github.event.inputs.dry_run == '1')) }} | |
| if: ${{ env.DRY_RUN != 'true' && env.DRY_RUN != '1' }} |
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -7,3 +7,4 @@ yarn-debug.log* | |
| yarn-error.log* | ||
| .pnpm-store | ||
| .DS_Store | ||
| Notion_API_Documentation_Hub.code-workspace | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,29 @@ | ||
| { | ||
| "workbench.colorCustomizations": { | ||
| "activityBar.activeBackground": "#2f7c47", | ||
| "activityBar.background": "#2f7c47", | ||
| "activityBar.foreground": "#e7e7e7", | ||
| "activityBar.inactiveForeground": "#e7e7e799", | ||
| "commandCenter.border": "#e7e7e799", | ||
| "editorGroup.border": "#2f7c47", | ||
| "panel.border": "#2f7c47", | ||
| "sash.hoverBorder": "#2f7c47", | ||
| "sideBar.border": "#2f7c47", | ||
| "statusBar.background": "#215732", | ||
| "statusBar.border": "#215732", | ||
| "statusBar.debuggingBackground": "#572146", | ||
| "statusBar.debuggingBorder": "#572146", | ||
| "statusBar.debuggingForeground": "#e7e7e7", | ||
| "statusBar.foreground": "#e7e7e7", | ||
| "statusBarItem.hoverBackground": "#2f7c47", | ||
| "statusBarItem.remoteBackground": "#215732", | ||
| "statusBarItem.remoteForeground": "#e7e7e7", | ||
| "tab.activeBorder": "#2f7c47", | ||
| "titleBar.activeBackground": "#215732", | ||
| "titleBar.activeForeground": "#e7e7e7", | ||
| "titleBar.border": "#215732", | ||
| "titleBar.inactiveBackground": "#21573299", | ||
| "titleBar.inactiveForeground": "#e7e7e799" | ||
| }, | ||
| "peacock.color": "#215732" | ||
| } |
Large diffs are not rendered by default.
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,2 +1,80 @@ | ||
| # Notion_API_Documentation_Hub | ||
| CF Worker that parses API documention and creates call cards on the API Hub in Notion. | ||
| # Notion API Documentation Hub | ||
|
|
||
| Cloudflare Worker that parses Notion pages for API documentation and creates structured "call cards" in your Notion API Hub. It streamlines keeping your API catalog up to date by syncing secrets from 1Password and deploying via GitHub Actions. | ||
|
|
||
| ## One‑click Deploy | ||
|
|
||
| Deploy this Worker to your Cloudflare account: | ||
|
|
||
| [](https://deploy.workers.cloudflare.com/?url=https://github.com/PCWProps/Notion_API_Documentation_Hub) | ||
|
|
||
| ## Prerequisites | ||
|
|
||
| - Node.js 18+ (Node 20 recommended) | ||
| - Cloudflare account and a Workers project | ||
| - 1Password account (Service Account recommended) or 1Password Connect | ||
|
|
||
| ## Install | ||
|
|
||
| ```bash | ||
| npm install | ||
| ``` | ||
|
|
||
| This repo pins Wrangler in devDependencies, so the `wrangler` command will resolve locally. | ||
|
|
||
| ## Configure | ||
|
|
||
| 1. Copy or prepare your secrets maps in the repo root: | ||
| - `secrets.map.json` (default) | ||
| - `secrets.map.staging.json` (optional, used automatically on `staging` branch) | ||
| Each map should be a JSON object mapping Cloudflare secret names to 1Password item fields, for example: | ||
| ```json | ||
| { | ||
| "NOTION_API_KEY": "op://MyVault/Notion API Key/credential", | ||
| "CLOUDFLARE_ACCOUNT_ID": "op://MyVault/Cloudflare Account/Account ID" | ||
| } | ||
| ``` | ||
| 2. Create GitHub Actions repo secrets (Settings → Secrets and variables → Actions): | ||
| - `OP_SERVICE_ACCOUNT_TOKEN` (preferred) or `OP_CONNECT_HOST` + `OP_CONNECT_TOKEN` | ||
| - `CLOUDFLARE_API_TOKEN` (with permissions to manage Workers secrets and deploy) | ||
|
|
||
| ## Local Development | ||
|
|
||
| ```bash | ||
| npm run dev | ||
| ``` | ||
|
|
||
| This runs `wrangler dev` using your local environment. You can set local environment variables or use a `.env` file for development only. The CI sync script does not source `.env`; it only parses simple KEY=VALUE lines to avoid executing non-shell content. | ||
|
|
||
| ## Deploy | ||
|
|
||
| From CI: Push to `main`/`Main` or run the workflow manually. The workflow will: | ||
|
|
||
| 1. Install dependencies and 1Password CLI | ||
| 2. Sync secrets from 1Password into Cloudflare Worker secrets | ||
| 3. Deploy via `npx wrangler deploy` | ||
|
|
||
| Manual deploy from your machine (optional): | ||
|
|
||
| ```bash | ||
| npx wrangler deploy | ||
| ``` | ||
|
|
||
| ## CI Dry Run | ||
|
|
||
| Trigger the workflow via "Run workflow" and set `dry_run: true` to verify secret resolution without writing to Cloudflare. You’ll see `[DRY_RUN] would set secret: ...` lines and the deploy step will be skipped. | ||
|
|
||
| ## Project Structure | ||
|
|
||
| - `src/` — Worker source | ||
| - `scripts/sync-secrets.sh` — Syncs 1Password secrets to Cloudflare Worker secrets using `secrets.map*.json` | ||
| - `.github/workflows/deploy.yml` — CI deploy pipeline | ||
|
|
||
| ## Troubleshooting | ||
|
|
||
| - Syntax error near `(` in CI usually indicates the shell tried to execute non-shell content. The workflow and scripts here avoid that by using quoted heredocs and strict parsing. | ||
| - Ensure GitHub secrets are set and that your `secrets.map*.json` paths are valid 1Password references. | ||
|
|
||
| ## License | ||
|
|
||
| See `LICENSE`. |
| Original file line number | Diff line number | Diff line change | ||||||
|---|---|---|---|---|---|---|---|---|
|
|
@@ -23,9 +23,9 @@ if [[ "${1:-}" == "--from-env" ]]; then | |||||||
| MODE_FROM_ENV=1 | ||||||||
| fi | ||||||||
|
|
||||||||
| MAP_FILE="${SECRETS_MAP:-[secrets.map](http://secrets.map).json}" | ||||||||
| if [[ "${GITHUB_REF_NAME:-}" == "staging" && -z "${SECRETS_MAP:-}" && -f "[secrets.map](http://secrets.map).staging.json" ]]; then | ||||||||
| MAP_FILE="[secrets.map](http://secrets.map).staging.json" | ||||||||
| MAP_FILE="${SECRETS_MAP:-secrets.map.json}" | ||||||||
| if [[ "${GITHUB_REF_NAME:-}" == "staging" && -z "${SECRETS_MAP:-}" && -f "secrets.map.staging.json" ]]; then | ||||||||
| MAP_FILE="secrets.map.staging.json" | ||||||||
| fi | ||||||||
|
|
||||||||
| ensure_tools() { | ||||||||
|
|
@@ -35,7 +35,9 @@ ensure_tools() { | |||||||
|
|
||||||||
| put_secret() { | ||||||||
| local key="$1" val="$2" | ||||||||
| if [[ -n "${DRY_RUN:-}" && "$DRY_RUN" != "0" ]]; then | ||||||||
| local dr="${DRY_RUN:-}" | ||||||||
| dr="${dr,,}" | ||||||||
| if [[ "$dr" == "1" || "$dr" == "true" ]]; then | ||||||||
| echo "[DRY_RUN] would set secret: $key" | ||||||||
| else | ||||||||
| printf "%s" "$val" | wrangler secret put "$key" --quiet | ||||||||
|
|
@@ -48,14 +50,28 @@ sync_from_env() { | |||||||
| if [[ ! -f .env ]]; then | ||||||||
| echo ".env not found" >&2; exit 1 | ||||||||
| fi | ||||||||
| # shellcheck disable=SC2046 | ||||||||
| set -a; source .env; set +a | ||||||||
| while IFS='=' read -r k v; do | ||||||||
| [[ -z "$k" || "$k" =~ ^# ]] && continue | ||||||||
| k_trim="${k%% *}"; v_trim="${!k_trim:-}" | ||||||||
| [[ -z "$v_trim" ]] && continue | ||||||||
| put_secret "$k_trim" "$v_trim" | ||||||||
| done < <(grep -E '^[A-Za-z_][A-Za-z0-9_]*=' .env || true) | ||||||||
| # Parse simple KEY=VALUE lines without sourcing to avoid executing arbitrary content | ||||||||
| while IFS= read -r line; do | ||||||||
| # trim leading/trailing whitespace | ||||||||
| trimmed="${line#${line%%[![:space:]]*}}" # remove leading | ||||||||
| trimmed="${trimmed%${trimmed##*[![:space:]]}}" # remove trailing | ||||||||
|
Comment on lines
+56
to
+57
|
||||||||
| trimmed="${line#${line%%[![:space:]]*}}" # remove leading | |
| trimmed="${trimmed%${trimmed##*[![:space:]]}}" # remove trailing | |
| trimmed=$(echo "$line" | sed 's/^[[:space:]]*//;s/[[:space:]]*$//') |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
The logical OR operator
||in GitHub Actions expressions will always evaluate to 'false' whengithub.event.inputs.dry_runis falsy, but this doesn't handle the case where the workflow is triggered by push events (wheregithub.event.inputs.dry_runis undefined). Use a ternary operator instead:${{ github.event_name == 'workflow_dispatch' && github.event.inputs.dry_run || '' }}