@koda-sl/baker-cli 0.188.0 → 0.189.1

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/README.md CHANGED
@@ -297,6 +297,7 @@ Read it before interpreting any null. It does not fire on the `--out` path (rows
297
297
  |------------------------|------------------------------------------|--------------------|
298
298
  | `campaign-performance` | Campaign metrics overview | LAST_30_DAYS |
299
299
  | `keyword-analysis` | Keyword performance per ad group | LAST_30_DAYS |
300
+ | `keyword-serving` | Why a keyword is limited — status reasons, first-page bid estimate vs max CPC, quality score | ALL_TIME |
300
301
  | `positive-keywords` | Positive (targeting) keywords only | ALL_TIME |
301
302
  | `negative-keywords` | Negative (blocking) keywords only | ALL_TIME |
302
303
  | `negative-keyword-lists` | Shared negative lists + their terms | ALL_TIME |
@@ -309,6 +310,10 @@ Read it before interpreting any null. It does not fire on the `--out` path (rows
309
310
 
310
311
  Every preset except the negatives lists and `account-summary` filters to **actually-serving entities** by default — the full status chain (`campaign.status = 'ENABLED' AND ad_group.status = 'ENABLED' AND ad_group_ad.status = 'ENABLED'`, as applicable) — and selects the status columns so you can see them. Pass `--include-paused` to widen to `!= 'REMOVED'` (keeps paused, still drops removed). Raw GAQL (no `--preset`) has no such default: a query over a serving-hierarchy resource without a status filter emits a `SERVING_SCOPE` warning reminding you to add the chain, because Google Ads has no single serving flag.
311
312
 
313
+ **"Eligible (Limited)" keywords:** an enabled keyword that barely shows is invisible in the performance presets — near-zero impressions look the same whether it is outbid, low quality, or rarely searched. `--preset keyword-serving` reads the signals behind Google Ads' status column: `ad_group_criterion.primary_status` and `primary_status_reasons` (the status enum has no `LIMITED` value — "(Limited)" lives in the reasons while the status stays `ELIGIBLE`), `position_estimates.first_page_cpc_micros` (the number in "Below first page bid (€3.63)"), the max CPC actually in force and where it comes from, quality score split into ad relevance / landing page / expected CTR, approval status, and `system_serving_status`. Any read whose rows carry those fields — preset or raw GAQL — comes back with a `KEYWORD_SERVING_LIMITED` warning naming the affected keywords (each by its ad group, since one keyword's copies share a criterion id) and the bid each would need. Below-first-page-bid and low-quality want opposite fixes (raise the bid vs. improve relevance), so the warning reports them separately. On `--out` the verdict is folded across pages as they stream to disk and returned on the file summary; as with `MISSING_FIELDS`, `--output csv|jsonl|md` emits rows only and carries no warnings.
314
+
315
+ The warning defers to Google: when the query selects `primary_status_reasons`, a keyword Google did not flag is not reported, even if its bid sits under the first-page estimate — the estimate is advisory and the bid may not be the criterion's to set under a portfolio strategy. Only an estimates-only read (no reasons selected) falls back to inferring the limit from the bid gap.
316
+
312
317
  **Pre-flight checks and auto-fixes:**
313
318
 
314
319
  The CLI rejects or automatically corrects common GAQL mistakes before hitting the API:
@@ -5129,6 +5134,36 @@ Without `--slug` the command behaves as before (one creative record per publishe
5129
5134
 
5130
5135
  ## Landing Quality (`baker landing`)
5131
5136
 
5137
+ Two tools that bracket a landing build: **`inspiration`** before you design (what does good look like here?) and **`critique`** after you build (did this settle into generic defaults?).
5138
+
5139
+ ### `baker landing inspiration`
5140
+
5141
+ A searchable library of real landing-page sections. Each entry is one section of a real page: a screenshot, a standalone HTML+CSS reproduction with a measured fidelity score, a description of how it moves, and the transferable idea behind it — classified in the same vocabulary the landing skill teaches, so a hit is directly buildable.
5142
+
5143
+ ```bash
5144
+ baker landing inspiration search "pricing with a monthly/annual toggle" --scope all
5145
+ baker landing inspiration view <section id> # full DNA + screenshots + motion filmstrip
5146
+ baker landing inspiration code <section id> # the standalone bundle
5147
+ baker landing inspiration page <source id> # a whole page as a section sequence
5148
+ baker landing inspiration add https://linear.app --note "client likes this density"
5149
+ baker landing inspiration favorites # what this company has saved
5150
+ baker landing inspiration scrape <url> --out <dir> # capture any page now, synchronously
5151
+ ```
5152
+
5153
+ - **Hybrid search over three signals** — keywords, meaning, and *appearance* (the screenshot is embedded, so a query like "dark developer hero with a terminal" can match a section whose text never says "terminal"). Filters: `--type --composition --register --interaction --motion --media --device --theme --max-rank --min-craft --min-fidelity --domain --similar-to --scope --limit`.
5154
+ - **Screenshots are downloaded to `.baker/inspiration/`** so an agent can actually look at a result rather than read a description of it.
5155
+ - **`fidelity` says how much to trust the code.** A measured 0–1 match between the live section and our standalone re-render, always reported. Above ~0.95 the markup renders like the original; below ~0.75 the section is scroll- or JS-driven and it does not.
5156
+ - **`used_on_pages`** appears when a section shows up on more than one of that site's pages — a nav or footer they ship everywhere, which is a stronger reference than a one-off.
5157
+ - **The corpus is shared across companies; favorites are per-company**, and search defaults to this company's saved sections.
5158
+ - **`add` refuses a page Baker already serves**, along with preview and private addresses. For our own pages the source is in the workspace, so a capture would file a screenshot and reconstructed markup next to the real thing — and because the corpus is shared, a live client page admitted here would be readable by every other company.
5159
+ - **`add` and `favorite` are recorded on the chat as a "Reference page" change, marked already applied.** The save and the study both happen immediately; there is nothing left for publish to apply and nothing a discard takes back.
5160
+ - **Compact by default, `--full` when you have chosen something.** Every list command returns what you need to *pick* a row; the 600-character "why it works" paragraph, the classification facets and the markup ride behind `--full` on `search`, `view`, `page`, `favorites` and `code`. A default `favorites` used to cost more than a default search for a question — "what does this client keep saving?" — that the facets alone answer.
5161
+ - **`page_id` on every search row** is what `page <id>` takes, so "how does this page sequence its sections?" is reachable from a result rather than only right after `add`. `favorites --limit` is capped at 100.
5162
+ - **`add` studies in the background; `scrape` returns with the page on disk.** `add` grows the shared library and takes minutes, so it can never answer "build our page like this one" within the same turn. `scrape` runs the identical capture locally and blocks until it finishes, writing section screenshots, standalone markup, a whole-page reproduction and `report.html`. `--no-motion` roughly halves the runtime; `--no-mobile`, `--no-code` and `--no-report` skip further passes.
5163
+ - **Inspiration, never a clipboard.** Both `code` and `scrape` record what was consulted, and `critique`'s `originality` family blocks a publish that reuses a reference's copy verbatim.
5164
+
5165
+ ### `baker landing critique`
5166
+
5132
5167
  Deterministic design-quality critic for landing pages — an offline, no-LLM detector for the well-known "AI slop" tells (gradient text, overused fonts like Inter, side-tab colored borders, cream/parchment grounds, purple-on-heading palettes, buzzword copy, broken images, and more). It scores a landing's `.astro` source and returns findings tiered **block / warn / advisory**.
5133
5168
 
5134
5169
  ```bash
@@ -5146,7 +5181,9 @@ baker landing critique spring-offer summer-offer claude # score three landings
5146
5181
 
5147
5182
  - **Agent washing is a copy tell.** A page that claims autonomy ("fully autonomous", "while you sleep", "no human intervention") and never says anywhere what the buyer approves, overrides, or audits scores an `agent-washing` warn. One signal about oversight of the agent's actions — approval, review, override, undo/rollback, audit log, escalation — anywhere on the page clears it; the rule is page-scope precisely because the hero can defer the trust story to a section below it. Generic privacy boilerplate ("GDPR", "encrypted", "your data") deliberately does **not** clear it, since it appears in most footers and says nothing about who is in charge of the agent.
5148
5183
 
5149
- Output is the standard envelope `{ ok, data, hints }` with `data = { advisory, slug, overall, counts, dimensions, findings }`. `dimensions` scores seven design families (typography, color, borders_depth, motion, spacing, copy, integrity) 0–1 (higher is better); `counts` is the block/warn/advisory tally.
5184
+ - **The `originality` family compares your copy against inspiration sections you actually consulted.** It fires only on sections opened with `baker landing inspiration code`, so it flags facts rather than resemblances. Reusing a reference's headline, subhead, or CTA verbatim is block-tier.
5185
+
5186
+ Output is the standard envelope `{ ok, data, hints }` with `data = { advisory, slug, overall, counts, dimensions, findings }`. `dimensions` scores eight design families (typography, color, borders_depth, motion, spacing, copy, integrity, originality) 0–1 (higher is better); `counts` is the block/warn/advisory tally.
5150
5187
 
5151
5188
  ## Brand Fonts (`baker brand fonts`)
5152
5189