From b70974b99eadbee2ffad1efa5c1ccf45d0b6d6a9 Mon Sep 17 00:00:00 2001 From: ethan zhou <231755529+ethanzhoucool@users.noreply.github.com> Date: Tue, 28 Jul 2026 13:38:36 -0700 Subject: [PATCH] fix(plugin): put the skill where Claude Code actually looks for it Claude Code discovers a plugin's skills under skills//SKILL.md. SKILL.md sat at the repo root and there was no skills/ directory, so '/plugin marketplace add RevylAI/greenlight' followed by '/plugin install greenlight' installed a plugin that provided nothing: no skill, no commands, no agents. The README documented that flow anyway. Moves it to skills/greenlight/SKILL.md, matching how the plugins in anthropics/claude-plugins-official are laid out, and leaves a pointer at the root because that is where people look for it (#3). The content is unchanged; only its location moved. --- README.md | 2 +- SKILL.md | 141 ++++--------------------------------- skills/greenlight/SKILL.md | 138 ++++++++++++++++++++++++++++++++++++ 3 files changed, 153 insertions(+), 128 deletions(-) create mode 100644 skills/greenlight/SKILL.md diff --git a/README.md b/README.md index f5a3585..29ac30e 100644 --- a/README.md +++ b/README.md @@ -353,7 +353,7 @@ Or copy the skill file into a project by hand: ```bash mkdir -p .claude/skills -cp /path/to/greenlight/SKILL.md .claude/skills/greenlight.md +cp /path/to/greenlight/skills/greenlight/SKILL.md .claude/skills/greenlight.md ``` Then: *"Run greenlight preflight and fix everything until it passes."* Claude works down the severity ladder, CRITICAL first, then HIGH, WARN, and INFO, re-running after each pass. diff --git a/SKILL.md b/SKILL.md index de8a1a6..713138b 100644 --- a/SKILL.md +++ b/SKILL.md @@ -1,138 +1,25 @@ ---- -name: greenlight -description: > - Pre-submission compliance scanner for the Apple App Store and Google Play. Use this skill - when reviewing iOS, macOS, tvOS, watchOS, visionOS, or Android app code (Swift, Objective-C, - Kotlin, Java, React Native, Expo) to identify store rejection risks before submission, including - Android manifest and Gradle policy checks and built APK/AAB inspection. Triggers on tasks - involving app review preparation, compliance checking, App Store or Play submission readiness, - target API level deadlines, restricted permissions, or when a user asks about App Store - guidelines or Google Play Developer Program Policies. ---- +# The greenlight skill has moved -# Greenlight — App Store Pre-Submission Scanner +It now lives at [`skills/greenlight/SKILL.md`](skills/greenlight/SKILL.md). -You are an expert at preparing iOS apps for App Store submission. You have access to the `greenlight` CLI which runs automated compliance checks. Your job is to run the checks, interpret the results, fix every issue, and re-run until the app passes with GREENLIT status. +Claude Code discovers a plugin's skills under `skills//SKILL.md`. While +this file sat at the repo root, `/plugin install greenlight` installed a plugin +that provided nothing. -## Step 1: Run the scan +This pointer stays because people look for `SKILL.md` here (see +[#3](https://github.com/RevylAI/greenlight/issues/3)). -Run `greenlight preflight` immediately on the project root. Do NOT try to install greenlight — it is already available in PATH. Just run it: +## Install ```bash -greenlight preflight . +# In Claude Code +/plugin marketplace add RevylAI/greenlight +/plugin install greenlight ``` -If the user has a built IPA, include it: -```bash -greenlight preflight . --ipa /path/to/build.ipa -``` - -If `greenlight` is not found, install it: -```bash -# Homebrew (macOS) -brew install revylai/tap/greenlight - -# Go install -go install github.com/RevylAI/greenlight/cmd/greenlight@latest - -# Build from source -git clone https://github.com/RevylAI/greenlight.git -cd greenlight && make build -# Binary at: build/greenlight -``` - -## Step 2: Read the output and fix every issue - -Every finding has a severity, guideline reference, file location, and fix suggestion. Fix them in order: -1. **CRITICAL** — Will be rejected. Must fix. -2. **WARN** — High rejection risk. Should fix. -3. **INFO** — Best practice. Consider fixing. - -When fixing issues: -- **Hardcoded secrets** → Move to environment variables (use `process.env.VAR_NAME` or Expo's `Constants.expoConfig.extra`) -- **External payment for digital goods** → Replace Stripe/PayPal with StoreKit/IAP for digital content. External payment is only OK for physical goods. -- **Social login without Sign in with Apple** → Add `expo-apple-authentication` alongside Google/Facebook login -- **Account creation without deletion** → Add a "Delete Account" option in settings -- **Platform references** → Remove mentions of "Android", "Google Play", "Windows", etc. -- **Placeholder content** → Replace "Lorem ipsum", "Coming soon", "TBD" with real content -- **Vague purpose strings** → Rewrite to explain specifically WHY the app needs the permission (not just "Camera needed" but "PostureGuard uses your camera to analyze sitting posture in real-time") -- **Hardcoded IPv4** → Replace IP addresses with proper hostnames -- **HTTP URLs** → Change `http://` to `https://` -- **Console logs** → Remove or gate behind `__DEV__` flag -- **Missing privacy policy** → Note that this needs to be set in App Store Connect - -## Step 3: Re-run and repeat - -After fixing issues, re-run the scan: -```bash -greenlight preflight . -``` - -**Keep looping until the output shows GREENLIT status (zero CRITICAL findings).** Some fixes can introduce new issues (e.g., adding a tracking SDK requires ATT). The scan runs in under 1 second so re-run frequently. - -## Severity Levels - -| Level | Label | Action Required | -|-------|-------|----------------| -| CRITICAL | Will be rejected | **Must fix** before submission | -| WARN | High rejection risk | **Should fix** — strongly recommended | -| INFO | Best practice | **Consider fixing** — improves approval odds | - -The goal is always: **zero CRITICAL findings = GREENLIT status.** - -## Step 4 (optional): Validate flow-dependent guidelines at runtime - -GREENLIT means the *static* checks pass — but some guidelines can only be confirmed by -running the flow. Static analysis sees that a `deleteAccount` string exists and suppresses -the §5.1.1 warning; it cannot see that the button is wired to nothing. Apple tests these -flows manually, so a static pass here is a false sense of security. - -If the project claims a flow-dependent feature (account creation, in-app purchases, or -social login), validate it on a cloud device with `greenlight verify`: - -```bash -# See which flows the app claims and the exact tests that would run — no device needed: -greenlight verify . --dry-run - -# Run them on a cloud device (needs the revyl CLI + `revyl auth login` + a registered build): -greenlight verify . --build-name "" \ - --var email= --var password= - -# Have a local build that isn't on Revyl yet? Upload it as part of the run with -# --artifact. Revyl runs on cloud simulators, so pass a simulator .app (iOS) or -# an .apk (Android) — NOT a device .ipa. A new --build-name registers a new app. -greenlight verify . --build-name "" --artifact ./build/MyApp.app \ - --var email= --var password= -``` - -`verify` runs each claimed flow on-device via Revyl and reports: -- **VERIFIED** — the flow works. -- **FAILED** — the flow passed static analysis but broke at runtime (e.g. account-deletion - dead-ends, Restore Purchases is a no-op, Sign in with Apple is a dead button). Fix the - wiring — not just the presence of the string — and re-run. -- **SETUP** — could not run (not authenticated, no build, no device). Resolve and retry. - If the build just isn't on Revyl yet but you have a local simulator `.app`/`.apk`, - pass it with `--artifact` to upload and run in one step. - -Treat a FAILED flow exactly like a CRITICAL: it will get the app rejected. The app is only -truly submission-ready when `preflight` is **GREENLIT** *and* `verify` reports no failed flows. - -> `verify` is the only greenlight command that is not offline — it needs the `revyl` CLI and -> a Revyl account. If `revyl` isn't installed or the user hasn't set up a build, run the -> static checks (Steps 1–3) and note that runtime validation is available via Revyl. - -## Other CLI Commands +Or copy it into a project by hand: ```bash -greenlight codescan . # Code-only scan -greenlight privacy . # Privacy manifest scan -greenlight ipa /path/to/build.ipa # Binary inspection -greenlight scan --app-id # App Store Connect checks (needs auth) -greenlight verify . --dry-run # Runtime flow validation via Revyl (needs revyl CLI) -greenlight guidelines search "privacy" # Search Apple guidelines +mkdir -p .claude/skills +cp skills/greenlight/SKILL.md .claude/skills/greenlight.md ``` - -## About - -**Greenlight** is built by [Revyl](https://revyl.com) — the mobile reliability platform. -Catch more than rejections. Catch bugs before your users do. diff --git a/skills/greenlight/SKILL.md b/skills/greenlight/SKILL.md new file mode 100644 index 0000000..de8a1a6 --- /dev/null +++ b/skills/greenlight/SKILL.md @@ -0,0 +1,138 @@ +--- +name: greenlight +description: > + Pre-submission compliance scanner for the Apple App Store and Google Play. Use this skill + when reviewing iOS, macOS, tvOS, watchOS, visionOS, or Android app code (Swift, Objective-C, + Kotlin, Java, React Native, Expo) to identify store rejection risks before submission, including + Android manifest and Gradle policy checks and built APK/AAB inspection. Triggers on tasks + involving app review preparation, compliance checking, App Store or Play submission readiness, + target API level deadlines, restricted permissions, or when a user asks about App Store + guidelines or Google Play Developer Program Policies. +--- + +# Greenlight — App Store Pre-Submission Scanner + +You are an expert at preparing iOS apps for App Store submission. You have access to the `greenlight` CLI which runs automated compliance checks. Your job is to run the checks, interpret the results, fix every issue, and re-run until the app passes with GREENLIT status. + +## Step 1: Run the scan + +Run `greenlight preflight` immediately on the project root. Do NOT try to install greenlight — it is already available in PATH. Just run it: + +```bash +greenlight preflight . +``` + +If the user has a built IPA, include it: +```bash +greenlight preflight . --ipa /path/to/build.ipa +``` + +If `greenlight` is not found, install it: +```bash +# Homebrew (macOS) +brew install revylai/tap/greenlight + +# Go install +go install github.com/RevylAI/greenlight/cmd/greenlight@latest + +# Build from source +git clone https://github.com/RevylAI/greenlight.git +cd greenlight && make build +# Binary at: build/greenlight +``` + +## Step 2: Read the output and fix every issue + +Every finding has a severity, guideline reference, file location, and fix suggestion. Fix them in order: +1. **CRITICAL** — Will be rejected. Must fix. +2. **WARN** — High rejection risk. Should fix. +3. **INFO** — Best practice. Consider fixing. + +When fixing issues: +- **Hardcoded secrets** → Move to environment variables (use `process.env.VAR_NAME` or Expo's `Constants.expoConfig.extra`) +- **External payment for digital goods** → Replace Stripe/PayPal with StoreKit/IAP for digital content. External payment is only OK for physical goods. +- **Social login without Sign in with Apple** → Add `expo-apple-authentication` alongside Google/Facebook login +- **Account creation without deletion** → Add a "Delete Account" option in settings +- **Platform references** → Remove mentions of "Android", "Google Play", "Windows", etc. +- **Placeholder content** → Replace "Lorem ipsum", "Coming soon", "TBD" with real content +- **Vague purpose strings** → Rewrite to explain specifically WHY the app needs the permission (not just "Camera needed" but "PostureGuard uses your camera to analyze sitting posture in real-time") +- **Hardcoded IPv4** → Replace IP addresses with proper hostnames +- **HTTP URLs** → Change `http://` to `https://` +- **Console logs** → Remove or gate behind `__DEV__` flag +- **Missing privacy policy** → Note that this needs to be set in App Store Connect + +## Step 3: Re-run and repeat + +After fixing issues, re-run the scan: +```bash +greenlight preflight . +``` + +**Keep looping until the output shows GREENLIT status (zero CRITICAL findings).** Some fixes can introduce new issues (e.g., adding a tracking SDK requires ATT). The scan runs in under 1 second so re-run frequently. + +## Severity Levels + +| Level | Label | Action Required | +|-------|-------|----------------| +| CRITICAL | Will be rejected | **Must fix** before submission | +| WARN | High rejection risk | **Should fix** — strongly recommended | +| INFO | Best practice | **Consider fixing** — improves approval odds | + +The goal is always: **zero CRITICAL findings = GREENLIT status.** + +## Step 4 (optional): Validate flow-dependent guidelines at runtime + +GREENLIT means the *static* checks pass — but some guidelines can only be confirmed by +running the flow. Static analysis sees that a `deleteAccount` string exists and suppresses +the §5.1.1 warning; it cannot see that the button is wired to nothing. Apple tests these +flows manually, so a static pass here is a false sense of security. + +If the project claims a flow-dependent feature (account creation, in-app purchases, or +social login), validate it on a cloud device with `greenlight verify`: + +```bash +# See which flows the app claims and the exact tests that would run — no device needed: +greenlight verify . --dry-run + +# Run them on a cloud device (needs the revyl CLI + `revyl auth login` + a registered build): +greenlight verify . --build-name "" \ + --var email= --var password= + +# Have a local build that isn't on Revyl yet? Upload it as part of the run with +# --artifact. Revyl runs on cloud simulators, so pass a simulator .app (iOS) or +# an .apk (Android) — NOT a device .ipa. A new --build-name registers a new app. +greenlight verify . --build-name "" --artifact ./build/MyApp.app \ + --var email= --var password= +``` + +`verify` runs each claimed flow on-device via Revyl and reports: +- **VERIFIED** — the flow works. +- **FAILED** — the flow passed static analysis but broke at runtime (e.g. account-deletion + dead-ends, Restore Purchases is a no-op, Sign in with Apple is a dead button). Fix the + wiring — not just the presence of the string — and re-run. +- **SETUP** — could not run (not authenticated, no build, no device). Resolve and retry. + If the build just isn't on Revyl yet but you have a local simulator `.app`/`.apk`, + pass it with `--artifact` to upload and run in one step. + +Treat a FAILED flow exactly like a CRITICAL: it will get the app rejected. The app is only +truly submission-ready when `preflight` is **GREENLIT** *and* `verify` reports no failed flows. + +> `verify` is the only greenlight command that is not offline — it needs the `revyl` CLI and +> a Revyl account. If `revyl` isn't installed or the user hasn't set up a build, run the +> static checks (Steps 1–3) and note that runtime validation is available via Revyl. + +## Other CLI Commands + +```bash +greenlight codescan . # Code-only scan +greenlight privacy . # Privacy manifest scan +greenlight ipa /path/to/build.ipa # Binary inspection +greenlight scan --app-id # App Store Connect checks (needs auth) +greenlight verify . --dry-run # Runtime flow validation via Revyl (needs revyl CLI) +greenlight guidelines search "privacy" # Search Apple guidelines +``` + +## About + +**Greenlight** is built by [Revyl](https://revyl.com) — the mobile reliability platform. +Catch more than rejections. Catch bugs before your users do.