@patchstack/connect 0.5.7 → 0.5.8
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/AGENT-INSTALL.md +2 -2
- package/README.md +4 -4
- package/dist/{chunk-2K5SHFUM.js → chunk-4OHAYSV2.js} +1 -1
- package/dist/{chunk-2K5SHFUM.js.map → chunk-4OHAYSV2.js.map} +1 -1
- package/dist/cli.js +88 -4
- package/dist/cli.js.map +1 -1
- package/dist/index.cjs +86 -2
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +4 -3
- package/dist/index.d.ts +4 -3
- package/dist/index.js +86 -2
- package/dist/index.js.map +1 -1
- package/dist/protect.cjs +91 -3
- package/dist/protect.cjs.map +1 -1
- package/dist/protect.edge.js +4 -0
- package/dist/protect.edge.js.map +1 -1
- package/dist/protect.js +6 -2
- package/dist/protect.js.map +1 -1
- package/dist/{refresh-manifest-3YWIYENU.js → refresh-manifest-IE6SPHG6.js} +88 -4
- package/dist/refresh-manifest-IE6SPHG6.js.map +1 -0
- package/package.json +1 -1
- package/dist/refresh-manifest-3YWIYENU.js.map +0 -1
package/AGENT-INSTALL.md
CHANGED
|
@@ -88,7 +88,7 @@ This is a request, not a mechanism: nothing in the install depends on it. Do it
|
|
|
88
88
|
|
|
89
89
|
**If the request you were given includes a claim token**, pass it exactly as given: `npx @patchstack/connect setup --claim-token <token>`. The site is then created in the person's own Patchstack account and `setup` prints their dashboard link for it — there is no sign-in step to relay. The token comes only from the person's Patchstack dashboard; never invent one, never write it to a file, never print it back. If `setup` reports that the token had expired or was not recognised, the site is not connected: hand over the dashboard link it prints instead, and tell the person they can copy a fresh prompt from the dashboard.
|
|
90
90
|
|
|
91
|
-
In a hosted builder, run setup with `PATCHSTACK_ENVIRONMENT=sandbox` scoped to the workspace process/command, ensure the CLI's on-disk edits are adopted into the platform's persisted project state, then restart any already-running preview/server process so it loads the guard. Do not persist `"environment": "sandbox"` in `.patchstackrc.json`: deployed builds use the same committed files and report `production` only when the platform's own
|
|
91
|
+
In a hosted builder, run setup with `PATCHSTACK_ENVIRONMENT=sandbox` scoped to the workspace process/command, ensure the CLI's on-disk edits are adopted into the platform's persisted project state, then restart any already-running preview/server process so it loads the guard. Do not persist `"environment": "sandbox"` in `.patchstackrc.json`: deployed builds use the same committed files and report `production` only when the build platform's own variables say so — its tier (Vercel, Netlify, Render, Railway, GitLab CI) or a branch named `main`, `master`, `production`, `prod`, `release` or `live` (Cloudflare Pages and Workers Builds, AWS Amplify, GitHub Actions, GitLab CI without a tier); a preview, pull request or other branch there reports `sandbox`, as does the Replit workspace, while a Replit Deployment reports `production`. A build in a project the builder generated and builds for itself (Lovable, Replit) reports `production` without an override, because the edit preview is a dev server and a build is the publish step — which is exactly why the sandbox label belongs in the workspace process and not in a file. A scan on a developer's machine, in a CI runner this does not know (`CI=true` alone), or on a platform with no such signal reports `local` on its own, and the dashboard shows that app as configured, not deployed. A client-only SPA or a static site generator has no server request path to guard: `setup` says runtime protection does not apply and installs nothing for it; never call such a project protected.
|
|
92
92
|
|
|
93
93
|
**Finish by telling the user to refresh their preview.** The widget's "Report a vulnerability" button loads with the page, so a preview that was already open still shows the HTML from before setup — the button is missing there until it reloads. Nothing in the CLI can reach the user's browser, so relaying this is your job. Phrase it as a check rather than a required step: a builder that hot reloads, or a preview server you restarted, may have refreshed it already.
|
|
94
94
|
|
|
@@ -194,7 +194,7 @@ It is server-only. Never put it in the widget tag, client bundles, or public env
|
|
|
194
194
|
- Never invent or guess a UUID — the scan provisions it, the widget silently no-ops on a fake one.
|
|
195
195
|
- Never invent or guess a claim token either. One is only ever handed to you by the person, from their own Patchstack dashboard; pass it with `--claim-token` (or `PATCHSTACK_CLAIM_TOKEN`) and nowhere else — not into `.patchstackrc.json`, not into a committed file, not into your reply.
|
|
196
196
|
- The CLI never opens the dashboard link and never asks for Patchstack credentials.
|
|
197
|
-
- Label hosted workspace scans with `PATCHSTACK_ENVIRONMENT=sandbox` in that process only. Leave production builds unset (a platform's own production
|
|
197
|
+
- Label hosted workspace scans with `PATCHSTACK_ENVIRONMENT=sandbox` in that process only. Leave production builds unset (a platform's own tier or production branch name, or the hosted builder the project belongs to, makes the build report `production`; a developer machine or a CI runner this does not know reports `local`) and never commit a sandbox label into files shared with production.
|
|
198
198
|
- If a step fails, stop and report it. Don't proceed with placeholders.
|
|
199
199
|
- CI never has the credential in a file: `.patchstackrc.local.json` is git-ignored by design, so set `PATCHSTACK_API_KEY` as an env var there (and `PATCHSTACK_SITE_UUID` too where `.patchstackrc.json` is also absent). Precedence for the site UUID and settings: CLI flag → env var → `.patchstackrc.json`. For the API key: env var → `.patchstackrc.local.json` → `.patchstackrc.json` (where installs made before the split still hold it). `login` is interactive and refuses to run in CI, so CI always takes its credential from the environment.
|
|
200
200
|
|
package/README.md
CHANGED
|
@@ -208,7 +208,7 @@ Environment variables:
|
|
|
208
208
|
- `PATCHSTACK_SITE_UUID` — the site UUID from your Patchstack dashboard
|
|
209
209
|
- `PATCHSTACK_ENDPOINT` — override the API endpoint (default `https://api.patchstack.com/monitor/pulse/manifest`)
|
|
210
210
|
- `PATCHSTACK_TIMEOUT_MS` — request timeout in milliseconds (default `30000`)
|
|
211
|
-
- `PATCHSTACK_ENVIRONMENT` — manifest label: `production`, `sandbox` or `local`. Unset, the label comes from the
|
|
211
|
+
- `PATCHSTACK_ENVIRONMENT` — manifest label: `production`, `sandbox` or `local`. Unset, the label comes from the build platform's own variables. Where the platform names the tier (Vercel, Netlify, Render, Railway, GitLab CI), production reports `production` and a preview `sandbox`. Where it names only the branch (Cloudflare Pages and Workers Builds, AWS Amplify, GitHub Actions, GitLab CI without a tier), a branch named `main`, `master`, `production`, `prod`, `release` or `live` reports `production` and any other branch or a pull request `sandbox`. A Replit Deployment reports `production`, the Replit workspace `sandbox`. Failing all of that, a project a hosted builder generated and builds for itself (Lovable, Replit) reports `production`, because on those platforms the edit preview is a dev server and a build only happens when the owner publishes. Anything else — a developer machine, a CI runner this does not know (`CI=true` alone), a platform this does not know — reports `local`
|
|
212
212
|
- `PATCHSTACK_CLAIM_TOKEN` — connect the site straight to your account (see *Connecting straight to your account*)
|
|
213
213
|
|
|
214
214
|
Two files, because one value is public and the other is not.
|
|
@@ -257,7 +257,7 @@ The token names your account, not the project: it is never written to `.patchsta
|
|
|
257
257
|
|
|
258
258
|
### Sandbox and production manifests
|
|
259
259
|
|
|
260
|
-
Every `scan` sends an environment label with its dependency manifest. When nothing sets one, the label comes from the
|
|
260
|
+
Every `scan` sends an environment label with its dependency manifest. When nothing sets one, the label comes from the build platform's own variables. Platforms that name the tier answer directly: Vercel's `VERCEL_ENV`, Netlify's `CONTEXT`, Render's pull-request flag, Railway's environment name, GitLab's `CI_ENVIRONMENT_TIER`. Production reports `production`; a preview those platforms name as such reports `sandbox`. Platforms that name only the branch — Cloudflare Pages and Workers Builds, AWS Amplify, GitHub Actions, GitLab CI without a tier — are decided by the branch name: `main`, `master`, `production`, `prod`, `release` and `live` report `production`, any other branch reports `sandbox`, and a pull-request build reports `sandbox` whatever the branch. That is an assumption about naming, so the line `scan` prints says the decision rests on the branch name; set `PATCHSTACK_ENVIRONMENT` where the live branch is called something else. A Replit Deployment reports `production` and the Replit workspace `sandbox`. Where no platform answers, the project itself gets the last word: one a hosted builder generated and builds for itself — Lovable, Replit — reports `production`, because the edit preview there is a dev server, so a build running at all is the owner publishing. Everything else reports `local` — a developer's machine, a CI runner this does not know (`CI=true` alone proves automation, not deployment), and a platform whose build environment carries no such signal. A local manifest is inventory — it tells Patchstack what the app is built from — and never counts as contact with a live site, so an app that has only been set up on a laptop shows in the dashboard as **Configured locally**, not as connected or deployed. The label also decides whether `mark-build` stamps the live-site marker, so a deployment that reads `local` ships its pages without one: set `PATCHSTACK_ENVIRONMENT=production` where builds run on a platform this list does not know. Sandboxed builders should set `PATCHSTACK_ENVIRONMENT=sandbox` in the sandbox process only. Patchstack stores and deduplicates manifests per environment, so an iterative workspace scan does not replace the last production manifest.
|
|
261
261
|
|
|
262
262
|
Do not commit `"environment": "sandbox"` to `.patchstackrc.json` when the same files are deployed to production. Scope the variable to the sandbox command/process instead:
|
|
263
263
|
|
|
@@ -265,7 +265,7 @@ Do not commit `"environment": "sandbox"` to `.patchstackrc.json` when the same f
|
|
|
265
265
|
PATCHSTACK_ENVIRONMENT=sandbox npx @patchstack/connect setup
|
|
266
266
|
```
|
|
267
267
|
|
|
268
|
-
The generated `prebuild` scan deliberately carries no hard-coded environment. A production build with no override reports `production` only because the platform's own
|
|
268
|
+
The generated `prebuild` scan deliberately carries no hard-coded environment. A production build with no override reports `production` only because the platform's own variables — its tier, or its branch name — say it is one; a preview or pull request on those platforms reports `sandbox` by itself, and a hosted builder's *workspace* must receive `PATCHSTACK_ENVIRONMENT=sandbox` from its host (the Replit workspace reports `sandbox` on its own) — its published build needs no override, because a build in such a project is the publish step. Runtime protection itself is not environment-specific: `PATCHSTACK_ENVIRONMENT` labels manifests only. Use `PATCHSTACK_MODE=dry-run` when protection should observe rather than block.
|
|
269
269
|
|
|
270
270
|
During a build, the `prebuild` scan removes any previous map stamp. A later `map --upload` in the same pre-bundle lifecycle hashes the map's policy content (excluding analyser timing and memory observations) and records that identity in the guard's existing rules file. The guard presents it on the rules request it already makes; only an explicit Patchstack confirmation naming the same map lets a rule scoped to one of your app's parameter names block. A build with no confirmed identity still enforces every ordinary rule — only scoped rules drop to detect-only, with the reason reported. Outside a pre-bundle hook, `map --upload` changes no file and sends no identity. See "Which build a rule belongs to" in `AGENT-INSTALL.md`.
|
|
271
271
|
|
|
@@ -311,7 +311,7 @@ The widget is a floating "Report a vulnerability" button — a disclosure channe
|
|
|
311
311
|
|
|
312
312
|
Re-runs update the tag in place (the `data-patchstack-connect-widget` attribute marks it as connector-managed); a pre-existing manual widget tag is left untouched. `--dry-run` never edits anything; a failed post still skips the widget tag (it needs the site UUID) but the production marker may already have been written, since it runs before the post. Projects whose root layout is code rather than HTML (Next.js, Nuxt, Astro, …) get the exact snippet and target file printed instead — `guide` shows framework-specific placement.
|
|
313
313
|
|
|
314
|
-
- **`mark-build`** ensures the same tag in built HTML output, covering builds whose source shell the connector couldn't edit, and stamps `window.__PATCHSTACK_PROD__` so the widget hides the claim/login UI on the published site (owners reach it by appending `#patchstack` to the live URL). The marker says the page is the live site, so **only a production build carries it**: the environment is read the same way `scan` reads it (the
|
|
314
|
+
- **`mark-build`** ensures the same tag in built HTML output, covering builds whose source shell the connector couldn't edit, and stamps `window.__PATCHSTACK_PROD__` so the widget hides the claim/login UI on the published site (owners reach it by appending `#patchstack` to the live URL). The marker says the page is the live site, so **only a production build carries it**: the environment is read the same way `scan` reads it (the build platform's own tier or branch name, then the hosted builder the project belongs to), and a local or preview build gets the widget tag, no marker, and any marker an earlier build left behind removed. Publishing a static build by hand from your machine is the case that needs `--production` (or `PATCHSTACK_ENVIRONMENT=production`), because nothing in that environment can say the build is a deployment.
|
|
315
315
|
|
|
316
316
|
- **Opting out:** persist `"widget": false` in `.patchstackrc.json` to disable both the widget tag and the production marker (dependency scanning only). Without it, the next successful scan re-adds the managed tag, and the next scan re-adds the marker on a JSX root.
|
|
317
317
|
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"sources":["../src/protect/safe-origin.js","../src/types.ts","../src/endpoint-policy.ts","../src/bounded-response.ts","../src/pulse-token.ts","../src/build-id.ts"],"mappings":";AAKO,SAAS,aAAa,OAAO;AAClC,MAAI;AACF,UAAM,IAAI,IAAI,IAAI,KAAK;AACvB,QAAI,EAAE,aAAa,SAAU,QAAO;AACpC,WAAO,EAAE,aAAa,YAAY,EAAE,aAAa,eAAe,EAAE,aAAa,eAAe,EAAE,aAAa,WAAW,EAAE,aAAa;AAAA,EACzI,QAAQ;AACN,WAAO;AAAA,EACT;AACF;AAMO,SAAS,YAAY,WAAW,UAAU,OAAO;AACtD,MAAI,OAAO,cAAc,YAAY,cAAc,GAAI,QAAO;AAC9D,MAAI,aAAa,SAAS,EAAG,QAAO;AACpC,WAAS,OAAO,gCAAgC,KAAK,cAAc,SAAS,qDAAqD;AACjI,SAAO;AACT;AAEA,IAAM,SAAS,oBAAI,IAAI;AACvB,SAAS,SAAS,KAAK,SAAS;AAC9B,MAAI,OAAO,IAAI,GAAG,EAAG;AACrB,SAAO,IAAI,GAAG;AAEd,UAAQ,KAAK,OAAO;AACtB;;;
|
|
1
|
+
{"version":3,"sources":["../src/protect/safe-origin.js","../src/types.ts","../src/endpoint-policy.ts","../src/bounded-response.ts","../src/pulse-token.ts","../src/build-id.ts"],"mappings":"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","names":[]}
|
package/dist/cli.js
CHANGED
|
@@ -1338,8 +1338,8 @@ function computeManifestChecksum(packages) {
|
|
|
1338
1338
|
var RULES = [
|
|
1339
1339
|
{ platform: "netlify", any: ["NETLIFY", "NETLIFY_BUILD_BASE", "DEPLOY_PRIME_URL"] },
|
|
1340
1340
|
{ platform: "vercel", any: ["VERCEL", "VERCEL_ENV", "VERCEL_URL"] },
|
|
1341
|
-
{ platform: "cloudflare", any: ["CF_PAGES", "CF_PAGES_URL", "CLOUDFLARE_ACCOUNT_ID"] },
|
|
1342
|
-
{ platform: "aws", any: ["AWS_APP_ID", "AWS_LAMBDA_FUNCTION_NAME", "AWS_EXECUTION_ENV"] },
|
|
1341
|
+
{ platform: "cloudflare", any: ["CF_PAGES", "CF_PAGES_URL", "WORKERS_CI", "WORKERS_CI_BRANCH", "CLOUDFLARE_ACCOUNT_ID"] },
|
|
1342
|
+
{ platform: "aws", any: ["AWS_APP_ID", "AWS_BRANCH", "AWS_LAMBDA_FUNCTION_NAME", "AWS_EXECUTION_ENV"] },
|
|
1343
1343
|
{ platform: "render", any: ["RENDER", "RENDER_SERVICE_ID", "RENDER_EXTERNAL_URL"] },
|
|
1344
1344
|
{ platform: "railway", any: ["RAILWAY_ENVIRONMENT", "RAILWAY_ENVIRONMENT_NAME", "RAILWAY_PROJECT_ID"] },
|
|
1345
1345
|
{ platform: "fly", any: ["FLY_APP_NAME", "FLY_REGION", "FLY_ALLOC_ID"] },
|
|
@@ -2146,6 +2146,17 @@ import { randomUUID as randomUUID2 } from "crypto";
|
|
|
2146
2146
|
import { readFileSync as readFileSync2 } from "fs";
|
|
2147
2147
|
import path6 from "path";
|
|
2148
2148
|
var set = (value) => value !== void 0 && value !== "";
|
|
2149
|
+
var PRODUCTION_BRANCHES = /* @__PURE__ */ new Set([
|
|
2150
|
+
"main",
|
|
2151
|
+
"master",
|
|
2152
|
+
"production",
|
|
2153
|
+
"prod",
|
|
2154
|
+
"release",
|
|
2155
|
+
"live"
|
|
2156
|
+
]);
|
|
2157
|
+
function environmentFromBranch(variable, branch) {
|
|
2158
|
+
return PRODUCTION_BRANCHES.has(branch.toLowerCase()) ? { environment: "production", evidence: `${variable}=${branch} (a production branch by name)` } : { environment: "sandbox", evidence: `${variable}=${branch} (not a production branch by name)` };
|
|
2159
|
+
}
|
|
2149
2160
|
var DISCRIMINATORS = [
|
|
2150
2161
|
{
|
|
2151
2162
|
platform: "vercel",
|
|
@@ -2174,6 +2185,79 @@ var DISCRIMINATORS = [
|
|
|
2174
2185
|
if (!set(env.RAILWAY_ENVIRONMENT_NAME)) return null;
|
|
2175
2186
|
return env.RAILWAY_ENVIRONMENT_NAME === "production" ? { environment: "production", evidence: "RAILWAY_ENVIRONMENT_NAME=production" } : { environment: "sandbox", evidence: `RAILWAY_ENVIRONMENT_NAME=${env.RAILWAY_ENVIRONMENT_NAME}` };
|
|
2176
2187
|
}
|
|
2188
|
+
},
|
|
2189
|
+
{
|
|
2190
|
+
// Pages and Workers Builds both name the branch and neither names the tier.
|
|
2191
|
+
platform: "cloudflare",
|
|
2192
|
+
read: (env) => {
|
|
2193
|
+
if (set(env.CF_PAGES) && set(env.CF_PAGES_BRANCH)) {
|
|
2194
|
+
return environmentFromBranch("CF_PAGES_BRANCH", env.CF_PAGES_BRANCH);
|
|
2195
|
+
}
|
|
2196
|
+
if (set(env.WORKERS_CI) && set(env.WORKERS_CI_BRANCH)) {
|
|
2197
|
+
return environmentFromBranch("WORKERS_CI_BRANCH", env.WORKERS_CI_BRANCH);
|
|
2198
|
+
}
|
|
2199
|
+
return null;
|
|
2200
|
+
}
|
|
2201
|
+
},
|
|
2202
|
+
{
|
|
2203
|
+
// Amplify names the branch, and separately whether the build is a pull-request preview.
|
|
2204
|
+
platform: "aws",
|
|
2205
|
+
read: (env) => {
|
|
2206
|
+
if (!set(env.AWS_APP_ID) || !set(env.AWS_BRANCH)) return null;
|
|
2207
|
+
return set(env.AWS_PULL_REQUEST_ID) ? { environment: "sandbox", evidence: "AWS_PULL_REQUEST_ID set (a pull-request preview)" } : environmentFromBranch("AWS_BRANCH", env.AWS_BRANCH);
|
|
2208
|
+
}
|
|
2209
|
+
},
|
|
2210
|
+
{
|
|
2211
|
+
// A Deployment build carries `REPLIT_DEPLOYMENT`; the workspace carries `REPL_ID` alone. Read here,
|
|
2212
|
+
// before the hosted-builder rule, so a workspace build in a Replit project is not its publish step.
|
|
2213
|
+
platform: "replit",
|
|
2214
|
+
read: (env) => {
|
|
2215
|
+
if (set(env.REPLIT_DEPLOYMENT)) {
|
|
2216
|
+
return { environment: "production", evidence: "REPLIT_DEPLOYMENT set (a Replit Deployment build)" };
|
|
2217
|
+
}
|
|
2218
|
+
if (set(env.REPL_ID)) {
|
|
2219
|
+
return { environment: "sandbox", evidence: "REPL_ID set without REPLIT_DEPLOYMENT (the workspace)" };
|
|
2220
|
+
}
|
|
2221
|
+
return null;
|
|
2222
|
+
}
|
|
2223
|
+
},
|
|
2224
|
+
{
|
|
2225
|
+
// GitHub Pages deploys build here. A pull request checks out a merge ref whose name says nothing, so
|
|
2226
|
+
// the event is read first; a tag is a release; otherwise the branch name decides.
|
|
2227
|
+
platform: "github-actions",
|
|
2228
|
+
read: (env) => {
|
|
2229
|
+
if (env.GITHUB_ACTIONS !== "true") return null;
|
|
2230
|
+
if (set(env.GITHUB_EVENT_NAME) && env.GITHUB_EVENT_NAME.startsWith("pull_request")) {
|
|
2231
|
+
return { environment: "sandbox", evidence: `GITHUB_EVENT_NAME=${env.GITHUB_EVENT_NAME} (a pull-request build)` };
|
|
2232
|
+
}
|
|
2233
|
+
if (env.GITHUB_REF_TYPE === "tag") {
|
|
2234
|
+
return { environment: "production", evidence: "GITHUB_REF_TYPE=tag (a tag build)" };
|
|
2235
|
+
}
|
|
2236
|
+
if (!set(env.GITHUB_REF_NAME)) return null;
|
|
2237
|
+
return environmentFromBranch("GITHUB_REF_NAME", env.GITHUB_REF_NAME);
|
|
2238
|
+
}
|
|
2239
|
+
},
|
|
2240
|
+
{
|
|
2241
|
+
// The tier, when a job declares one, is GitLab's own word for it. Without one: a merge request is a
|
|
2242
|
+
// check, a tag is a release, the default branch goes live, and any other branch name decides.
|
|
2243
|
+
platform: "gitlab-ci",
|
|
2244
|
+
read: (env) => {
|
|
2245
|
+
if (env.GITLAB_CI !== "true") return null;
|
|
2246
|
+
if (set(env.CI_ENVIRONMENT_TIER)) {
|
|
2247
|
+
return env.CI_ENVIRONMENT_TIER === "production" ? { environment: "production", evidence: "CI_ENVIRONMENT_TIER=production" } : { environment: "sandbox", evidence: `CI_ENVIRONMENT_TIER=${env.CI_ENVIRONMENT_TIER}` };
|
|
2248
|
+
}
|
|
2249
|
+
if (set(env.CI_MERGE_REQUEST_IID)) {
|
|
2250
|
+
return { environment: "sandbox", evidence: "CI_MERGE_REQUEST_IID set (a merge-request build)" };
|
|
2251
|
+
}
|
|
2252
|
+
if (set(env.CI_COMMIT_TAG)) {
|
|
2253
|
+
return { environment: "production", evidence: "CI_COMMIT_TAG set (a tag build)" };
|
|
2254
|
+
}
|
|
2255
|
+
if (!set(env.CI_COMMIT_BRANCH)) return null;
|
|
2256
|
+
if (set(env.CI_DEFAULT_BRANCH) && env.CI_COMMIT_BRANCH === env.CI_DEFAULT_BRANCH) {
|
|
2257
|
+
return { environment: "production", evidence: `CI_COMMIT_BRANCH=${env.CI_COMMIT_BRANCH} (the default branch)` };
|
|
2258
|
+
}
|
|
2259
|
+
return environmentFromBranch("CI_COMMIT_BRANCH", env.CI_COMMIT_BRANCH);
|
|
2260
|
+
}
|
|
2177
2261
|
}
|
|
2178
2262
|
];
|
|
2179
2263
|
var HOSTED_BUILDER_PACKAGES = [
|
|
@@ -9113,7 +9197,7 @@ Environment:
|
|
|
9113
9197
|
PATCHSTACK_API_BASE API origin for /oauth/token and /api/logs/log (default: https://api.patchstack.com)
|
|
9114
9198
|
PATCHSTACK_ENDPOINT API endpoint (default: https://api.patchstack.com/monitor/pulse/manifest)
|
|
9115
9199
|
PATCHSTACK_TIMEOUT_MS Request timeout in ms (default: 30000; a scan that needs longer saves what worked to .patchstackrc.json)
|
|
9116
|
-
PATCHSTACK_ENVIRONMENT Manifest label: production, sandbox or local. Unset,
|
|
9200
|
+
PATCHSTACK_ENVIRONMENT Manifest label: production, sandbox or local. Unset, the build platform's own tier or branch name decides; a developer machine reports local.
|
|
9117
9201
|
PATCHSTACK_MODE (protect) Runtime guard mode: block (default) | dry-run
|
|
9118
9202
|
PATCHSTACK_ROUTE_WAF (protect) Set to 1 to also screen every request at the route level (opt-in)
|
|
9119
9203
|
|
|
@@ -9422,7 +9506,7 @@ async function runScan(args, options = {}) {
|
|
|
9422
9506
|
}
|
|
9423
9507
|
if (config.environment === "local") {
|
|
9424
9508
|
console.log(
|
|
9425
|
-
"Reporting from this machine as the local environment: the dashboard will show the app as configured, not deployed.
|
|
9509
|
+
"Reporting from this machine as the local environment: the dashboard will show the app as configured, not deployed. A build on a platform this recognises reports production or sandbox on its own; on a platform it does not know, set PATCHSTACK_ENVIRONMENT=production for the build that goes live."
|
|
9426
9510
|
);
|
|
9427
9511
|
} else {
|
|
9428
9512
|
const because = (config.environmentEvidence ?? []).length > 0 ? ` (${config.environmentEvidence.join("; ")})` : "";
|