@pikku/skills 0.12.35 → 0.12.37
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 +9 -4
- package/dist/index.d.ts +7 -4
- package/dist/index.js +9 -5
- package/dist/skills.gen.d.ts +1 -0
- package/dist/skills.gen.js +5 -3
- package/dist/snippets.d.ts +26 -0
- package/dist/snippets.js +148 -0
- package/package.json +2 -2
- package/skills/pikku-addon/SKILL.md +40 -24
- package/skills/pikku-addon/references/addon-package-manifest.md +9 -4
- package/skills/pikku-addon/references/openapi.md +99 -0
- package/skills/pikku-agent/references/agents.md +3 -1
- package/skills/pikku-auth/references/better-auth.md +16 -0
- package/skills/pikku-build/SKILL.md +18 -1
- package/skills/pikku-build/references/app.md +52 -4
- package/skills/pikku-build/references/feature.md +23 -96
- package/skills/pikku-build/references/quick.md +12 -3
- package/skills/pikku-changes/SKILL.md +172 -0
- package/skills/pikku-concepts/SKILL.md +33 -138
- package/skills/pikku-concepts/references/bootstrap.md +58 -0
- package/skills/pikku-concepts/references/concept-mapping.md +16 -0
- package/skills/pikku-concepts/references/language.md +87 -0
- package/skills/pikku-deploy/SKILL.md +1 -1
- package/skills/pikku-fabric/SKILL.md +13 -13
- package/skills/pikku-guide/SKILL.md +264 -0
- package/skills/pikku-kysely/SKILL.md +1 -1
- package/skills/pikku-n8n-import/SKILL.md +4 -3
- package/skills/pikku-react/references/client.md +12 -0
- package/skills/pikku-realtime/SKILL.md +6 -6
- package/skills/pikku-report/SKILL.md +143 -0
- package/skills/pikku-scenario/SKILL.md +71 -563
- package/skills/pikku-scenario/references/browser.md +59 -0
- package/skills/pikku-scenario/references/coverage.md +70 -0
- package/skills/pikku-scenario/references/personas.md +87 -0
- package/skills/pikku-scenario/references/steps.md +366 -0
- package/skills/pikku-service-backends/SKILL.md +1 -1
- package/skills/pikku-wiring/SKILL.md +1 -1
- package/skills/pikku-workflow/SKILL.md +7 -8
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
# What language you write in
|
|
2
|
+
|
|
3
|
+
Three different things in a Pikku project have a human language, and they are
|
|
4
|
+
**not** the same language. Collapsing them is the mistake this section exists to
|
|
5
|
+
prevent, and it has already shipped in a real product — the failure is at the
|
|
6
|
+
bottom.
|
|
7
|
+
|
|
8
|
+
| Axis | What it covers | What decides it |
|
|
9
|
+
| --------------- | ----------------------------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------------------------------------------------------------------------------- |
|
|
10
|
+
| **Identifiers** | Function, component, type, variable and file names. Database tables and columns. Branch names and commit messages. | Nothing. **Always English.** There is no setting. |
|
|
11
|
+
| **Meta** | The prose authored _inside_ the code: `description` on functions and steps, `name`/`title` on features and scenarios, step `template`, role/persona descriptions. | `metaLocale` in `pikku.config.json`. Defaults to `en`. |
|
|
12
|
+
| **Product UI** | Every string the app shows a user. | `messages/<locale>.json`, with `active.json`'s `defaultLocale` choosing what a first-time visitor opens in. |
|
|
13
|
+
|
|
14
|
+
## Identifiers are English, and nothing changes that
|
|
15
|
+
|
|
16
|
+
Not the product's market, not the team's working language, and **not `metaLocale`**.
|
|
17
|
+
A German medical practice, an Arabic marketplace and a Japanese logistics tool
|
|
18
|
+
all get `getOverview`, `AttentionStripe`, `case`, `event`.
|
|
19
|
+
|
|
20
|
+
This is not linguistic preference, it is mechanics. Identifiers are the surface
|
|
21
|
+
every other tool binds to: the generated `#pikku/*` clients, `pikku info` and
|
|
22
|
+
`pikku meta`, the RPC map a scenario's `actor.invoke` is typed over, the
|
|
23
|
+
generated SQL types, every skill and every agent that ever picks the project up.
|
|
24
|
+
A `vorgang` table types as `Vorgang` in Kysely and reads as noise to everyone who
|
|
25
|
+
did not name it, and unlike a string it cannot be translated later — renaming an
|
|
26
|
+
identifier is a migration, not an edit.
|
|
27
|
+
|
|
28
|
+
## Meta follows `metaLocale`, and that is what the field is for
|
|
29
|
+
|
|
30
|
+
```json
|
|
31
|
+
{ "metaLocale": "de" }
|
|
32
|
+
```
|
|
33
|
+
|
|
34
|
+
Meta is the one part of a project the **Pikku Console** renders back to a human.
|
|
35
|
+
A team reviewing their own functions, features and scenario reports in the
|
|
36
|
+
Console is reading meta and nothing else, so a team whose working language is
|
|
37
|
+
German should be able to read their Console in German. That is the entire reason
|
|
38
|
+
the field exists.
|
|
39
|
+
|
|
40
|
+
Read it before you author meta, and write descriptions, titles and templates in
|
|
41
|
+
it. Absent, it is `en`. It is a BCP-47 tag (`en`, `de`, `pt-BR` — a hyphen, not
|
|
42
|
+
an underscore), and the CLI rejects anything else by name.
|
|
43
|
+
|
|
44
|
+
`metaLocale` is **not** licence to rename anything. `metaLocale: "de"` buys a German
|
|
45
|
+
`description: 'Zeigt die Arbeitsliste'` on a function still called
|
|
46
|
+
`getWorklist`.
|
|
47
|
+
|
|
48
|
+
## Product UI language lives in the catalogue, and only there
|
|
49
|
+
|
|
50
|
+
What the app says to its users is a translation concern, not a code concern. It
|
|
51
|
+
belongs in `messages/<locale>.json`; `pikku-i18n` owns the details. The one rule
|
|
52
|
+
worth repeating here: **`baseLocale` in `project.inlang/settings.json` stays
|
|
53
|
+
`en`.** It names the message _source_ — the catalogue every other language is
|
|
54
|
+
cloned from and translated against — so a project that sets it to anything else
|
|
55
|
+
has no English catalogue to translate from and can never gain a second language
|
|
56
|
+
without re-authoring every key.
|
|
57
|
+
|
|
58
|
+
## The failure this comes from
|
|
59
|
+
|
|
60
|
+
An agent was asked to build a doctor's portal for a German practice. The brief
|
|
61
|
+
said "the entire UI is German, no English strings visible anywhere". The agent
|
|
62
|
+
read one sentence about the product's users as an instruction about the
|
|
63
|
+
codebase, and produced:
|
|
64
|
+
|
|
65
|
+
- `project.inlang/settings.json` with `baseLocale: "de"` and `locales: ["de"]`,
|
|
66
|
+
no `en.json` at all — which silently broke `--add-locale` forever
|
|
67
|
+
- RPC functions `getUebersicht` and `getPatientendetail`
|
|
68
|
+
- React components `Zeitstrahl` and `AufmerksamkeitStreifen`
|
|
69
|
+
- database tables `vorgang` and `ereignis`, with German columns
|
|
70
|
+
|
|
71
|
+
Every one of those is wrong, and the brief was satisfied by none of them: a
|
|
72
|
+
German UI needs German _messages_. What that project actually wanted was three
|
|
73
|
+
settings, each on its own axis:
|
|
74
|
+
|
|
75
|
+
```jsonc
|
|
76
|
+
// project.inlang/settings.json — the message source stays English
|
|
77
|
+
{ "baseLocale": "en", "locales": ["en", "de"] }
|
|
78
|
+
|
|
79
|
+
// apps/app/src/i18n/active.json — what a first-time visitor opens in
|
|
80
|
+
{ "defaultLocale": "de" }
|
|
81
|
+
|
|
82
|
+
// pikku.config.json — the language the team reads their Console in
|
|
83
|
+
{ "metaLocale": "de" }
|
|
84
|
+
```
|
|
85
|
+
|
|
86
|
+
Identifiers stay English throughout. When a brief tells you the product speaks a
|
|
87
|
+
language, it is telling you about axis three and nothing else.
|
|
@@ -21,7 +21,7 @@ Use this skill as an execution checklist, not reference material.
|
|
|
21
21
|
1. Discover before editing. Run the relevant `pikku meta ... --json` command and inspect only the focused output you need.
|
|
22
22
|
2. Identify the source files that own the behavior. Do not start by reading generated output, `.pikku`, `node_modules`, vendored packages, or broad build artifacts.
|
|
23
23
|
3. Make the smallest source change that satisfies the task. Keep generated files generated, and avoid hand-editing SDKs, schema output, or typegen.
|
|
24
|
-
4. Validate with the narrowest relevant command first, then run `pikku
|
|
24
|
+
4. Validate with the narrowest relevant command first, then run `pikku all` when functions, wirings, schemas, or generated clients may have changed.
|
|
25
25
|
5. If validation fails, fix the source cause and rerun validation. Do not paper over generated errors by editing generated files.
|
|
26
26
|
|
|
27
27
|
Signatures and option keys come from `pikku doc` — run `pikku doc --ai` for the
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: pikku-fabric
|
|
3
|
-
description: 'Build, convert and debug apps on the Pikku Fabric platform. Covers SQLite/libSQL database setup with Kysely, fabric project layout, deploy provider config, `
|
|
3
|
+
description: 'Build, convert and debug apps on the Pikku Fabric platform. Covers SQLite/libSQL database setup with Kysely, fabric project layout, deploy provider config, `pikkufabric.config.json`, the `pikku all` + `tsc` verification loop, and reading logs, traces and metrics from a deployed stage. TRIGGER when: user is working on a Fabric-hosted Pikku project, converting an app to Fabric format, asking about Fabric deployment, database or project conventions, asking about a `pikku fabric validate` finding including app-missing-actor-quick-login, or a deployed stage is erroring, timing out or behaving differently than local ("why is prod failing", "check the logs"). DO NOT TRIGGER when: user is working on a generic (non-Fabric) Pikku deployment — use pikku-deploy instead — or the failure reproduces locally, which is where to debug it.'
|
|
4
4
|
installGroups: [fabric]
|
|
5
5
|
---
|
|
6
6
|
|
|
@@ -18,7 +18,7 @@ Use this skill as an execution checklist, not reference material.
|
|
|
18
18
|
2. Discover before editing. Run the relevant `pikku meta ... --json` command and inspect only the focused output you need.
|
|
19
19
|
3. Identify the source files that own the behavior. Do not start by reading generated output, `.pikku`, `node_modules`, vendored packages, or broad build artifacts.
|
|
20
20
|
4. Make the smallest source change that satisfies the task. Keep generated files generated, and avoid hand-editing SDKs, schema output, or typegen.
|
|
21
|
-
5. Validate with the narrowest relevant command first, then run `pikku
|
|
21
|
+
5. Validate with the narrowest relevant command first, then run `pikku all` when functions, wirings, schemas, or generated clients may have changed.
|
|
22
22
|
6. If validation fails, fix the source cause and rerun validation. Do not paper over generated errors by editing generated files.
|
|
23
23
|
|
|
24
24
|
Fabric is a serverless deployment platform for Pikku apps. Every Fabric app runs on Cloudflare Workers with a SQLite database (via libSQL/Turso). This skill covers what's unique to Fabric. For general Pikku concepts, function authoring, HTTP wiring, and more, see `pikku-concepts`, `pikku-wiring`, `pikku-services`, etc.
|
|
@@ -31,20 +31,20 @@ Always run project discovery first:
|
|
|
31
31
|
yarn pikku meta context --json
|
|
32
32
|
```
|
|
33
33
|
|
|
34
|
-
|
|
34
|
+
Run `pikku meta` before grepping or editing a Fabric app.
|
|
35
35
|
|
|
36
|
-
-
|
|
37
|
-
-
|
|
38
|
-
-
|
|
39
|
-
-
|
|
36
|
+
- `pikku meta context --json` for the project map: functions, wires, workflows, capabilities, and source files.
|
|
37
|
+
- `pikku meta clients --json` before frontend/RPC work.
|
|
38
|
+
- `pikku meta functions --json` to list function ids, then `pikku meta functions get <id> --json` for one function.
|
|
39
|
+
- `pikku meta schemas --json` to list schema names. Only request a full schema body with `pikku meta schemas get <name> --json` when you need it.
|
|
40
40
|
|
|
41
41
|
Do not load every schema body by default; that wastes context and usually makes the model worse.
|
|
42
42
|
|
|
43
43
|
For database work:
|
|
44
44
|
|
|
45
|
-
- Use `pikku
|
|
46
|
-
- Use `pikku
|
|
47
|
-
- Do not inspect database credentials or connect to the database directly; Fabric
|
|
45
|
+
- Use `pikku fabric db schema [--branch <branch>]` for the actual attached Fabric database state: tables and columns.
|
|
46
|
+
- Use `pikku meta schemas` for code-level JSON Schema contracts, not database introspection.
|
|
47
|
+
- Do not inspect database credentials or connect to the database directly; Fabric already exposes the safe introspection surface.
|
|
48
48
|
|
|
49
49
|
## Database: SQLite via libSQL
|
|
50
50
|
|
|
@@ -437,16 +437,16 @@ the deploy with "local HEAD … ≠ remote …" even though your code is pushed.
|
|
|
437
437
|
|
|
438
438
|
Functions with `expose: true` are versioned via `versions.pikku.json`. When you change a function's input or output schema, you must bump its version number — otherwise `pikku all` will report a breaking change and callers' generated clients become stale.
|
|
439
439
|
|
|
440
|
-
|
|
440
|
+
`pikku all` catches this automatically.
|
|
441
441
|
|
|
442
442
|
## After every code change
|
|
443
443
|
|
|
444
|
-
|
|
444
|
+
Run `pikku all` after modifying functions, wirings, or schemas, then `tsc --noEmit`:
|
|
445
445
|
|
|
446
446
|
1. `pikku all` — regenerates all codegen, checks version compliance
|
|
447
447
|
2. `tsc --noEmit` — validates TypeScript types
|
|
448
448
|
|
|
449
|
-
|
|
449
|
+
Breaking changes are reported by the version check in step 1.
|
|
450
450
|
|
|
451
451
|
### `app-missing-actor-quick-login-<app>`
|
|
452
452
|
|
|
@@ -0,0 +1,264 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: pikku-guide
|
|
3
|
+
description: >-
|
|
4
|
+
Use when writing or regenerating a Pikku project's user guide — the end-user documentation
|
|
5
|
+
built from the scenario suite with `pikku scenario guide`. Pages are hand-written markdown that
|
|
6
|
+
cite features (pikkuFeature); the recordings and screenshots a passing `--screenshots` run
|
|
7
|
+
filed for each cited feature are merged in as figures. Covers writing the prose, the
|
|
8
|
+
`<!-- pikku:guide feature=… -->` markers, the capture step, `.guide.lock` staleness,
|
|
9
|
+
`document: false`, `--allow-undocumented`, `--artifact-base`, and the traps that make a guide
|
|
10
|
+
come out empty or refused. TRIGGER when: user asks for a user guide, help pages, docs with
|
|
11
|
+
screenshots, or "document the app". DO NOT TRIGGER when: user asks about API reference docs,
|
|
12
|
+
README files, or writing the scenarios themselves (use pikku-scenario).
|
|
13
|
+
installGroups: [core]
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
# Pikku Guide
|
|
17
|
+
|
|
18
|
+
A guide is the app explained to the people who use it, with the scenario suite
|
|
19
|
+
as its evidence. The suite proves what the product does and photographs it
|
|
20
|
+
doing it; the pages say what that means for the reader and how to do it.
|
|
21
|
+
|
|
22
|
+
Three inputs, one output:
|
|
23
|
+
|
|
24
|
+
| Input | Comes from | Owned by |
|
|
25
|
+
|---|---|---|
|
|
26
|
+
| Structure | `pikkuFeature` meta — which features exist, and that every one is cited | the suite |
|
|
27
|
+
| Evidence | the latest passing run under `.pikku/scenario-runs/` — recordings and screenshots | the run |
|
|
28
|
+
| Prose | markdown pages under `docs/` (or `--docs <dir>`) — **every word the reader reads** | a human, or you |
|
|
29
|
+
|
|
30
|
+
**The run contributes pictures, never words.** Step sentences, scenario
|
|
31
|
+
descriptions and feature names are written to prove a test, and none of them
|
|
32
|
+
reaches the page. A page that is a two-line intro and a marker publishes as a
|
|
33
|
+
wall of videos with no instructions — the most common way a guide comes out
|
|
34
|
+
bad. The writing in §2 is the job; the rest of this skill is plumbing.
|
|
35
|
+
|
|
36
|
+
`pikku scenario guide` writes one markdown file per source page into
|
|
37
|
+
`.pikku/guide/` (or `--output`). It renders no HTML, resolves no asset URLs and
|
|
38
|
+
calls no model. Images are ordinary relative `` references into
|
|
39
|
+
the run directory; whoever hosts the markdown rewrites them, or you pass
|
|
40
|
+
`--artifact-base /docs/_media/` for a host that serves them at a fixed address.
|
|
41
|
+
|
|
42
|
+
Read **pikku-scenario** first if the project has no features or browser steps
|
|
43
|
+
yet — the guide cannot be better than the suite under it.
|
|
44
|
+
|
|
45
|
+
## 1. A page cites a feature
|
|
46
|
+
|
|
47
|
+
A page is a markdown file with frontmatter and a marker pair where the block
|
|
48
|
+
belongs:
|
|
49
|
+
|
|
50
|
+
```markdown
|
|
51
|
+
---
|
|
52
|
+
title: Booking a course
|
|
53
|
+
description: Finding a course, taking a place, and what happens after.
|
|
54
|
+
---
|
|
55
|
+
|
|
56
|
+
Courses run one evening a week for eight weeks. Book when you know which
|
|
57
|
+
evening suits you; Intro to Improv is the place to start if you have never
|
|
58
|
+
done improv before.
|
|
59
|
+
|
|
60
|
+
1. Open **Courses**. Each course shows its evening and how many places are left.
|
|
61
|
+
2. Choose a course, then **Book a place**.
|
|
62
|
+
3. Confirm your details and choose **Book**.
|
|
63
|
+
|
|
64
|
+
Your place appears under **My bookings**, and a confirmation email follows.
|
|
65
|
+
|
|
66
|
+
<!-- pikku:guide feature=bookingsFeature -->
|
|
67
|
+
<!-- /pikku:guide -->
|
|
68
|
+
|
|
69
|
+
## The course says it is full
|
|
70
|
+
|
|
71
|
+
A full course keeps a waiting list. Choose **Join the waiting list** and we
|
|
72
|
+
email you the moment a place frees up — you are not charged until then.
|
|
73
|
+
|
|
74
|
+
## Can I switch to another evening?
|
|
75
|
+
|
|
76
|
+
Email us before the second week and we will move you if there is a place.
|
|
77
|
+
```
|
|
78
|
+
|
|
79
|
+
- `feature=` is the **exported identifier id** of the `pikkuFeature`, not its
|
|
80
|
+
display name.
|
|
81
|
+
- A rebuild rewrites only the region between the markers. Everything around
|
|
82
|
+
them is yours and survives every run.
|
|
83
|
+
- One page may cite several features; one feature may be cited by several
|
|
84
|
+
pages. The mapping is the union of every marker in the tree.
|
|
85
|
+
- Frontmatter the compiler does not own (`slug`, `sidebar_position`, `draft`)
|
|
86
|
+
passes through untouched.
|
|
87
|
+
|
|
88
|
+
The generated block is the feature's **figures and nothing else**: for each
|
|
89
|
+
scenario, its recordings first (one per actor), then its screenshots, deduped
|
|
90
|
+
across data-driven rows. Two strings from the suite do reach the page, as
|
|
91
|
+
captions:
|
|
92
|
+
|
|
93
|
+
| Figure | Caption |
|
|
94
|
+
|---|---|
|
|
95
|
+
| Recording | the scenario's `title`, then ` — ` and the actor's name |
|
|
96
|
+
| Screenshot | the `name` it was taken under |
|
|
97
|
+
|
|
98
|
+
So those two are user-facing copy: "Take a place on a course", "the course list,
|
|
99
|
+
with places left on each ticket" — not "mira books c-intro-1024" or
|
|
100
|
+
"courses /app/courses at 1440px". The scenario `description` and the steps are
|
|
101
|
+
never rendered.
|
|
102
|
+
|
|
103
|
+
A block is indivisible: all of a feature's figures land together, where the
|
|
104
|
+
marker sits. Place the marker after the steps it illustrates, not before them.
|
|
105
|
+
If one page needs figures beside two separate steps, those steps are two
|
|
106
|
+
features.
|
|
107
|
+
|
|
108
|
+
Organise pages by who reads them, not by feature: `docs/using/`,
|
|
109
|
+
`docs/teaching/`, `docs/organising/`. Use the project's own vocabulary, the one
|
|
110
|
+
on its screens — not internal table names.
|
|
111
|
+
|
|
112
|
+
## 2. Writing the page
|
|
113
|
+
|
|
114
|
+
Write it so a reader can do the task **with every figure removed**. The figures
|
|
115
|
+
confirm; they do not instruct. A reader skims for the step they are stuck on,
|
|
116
|
+
and cannot search a video.
|
|
117
|
+
|
|
118
|
+
Before writing, read the screen's component and its copy, then the feature's
|
|
119
|
+
scenarios. The screen is what renders; the scenario is what is proven, and its
|
|
120
|
+
steps are the user's journey already in order. Write only what you have seen
|
|
121
|
+
in one of them — a fluent page describing a flow that does not exist is worse
|
|
122
|
+
than no page.
|
|
123
|
+
|
|
124
|
+
Each task page carries, in the reader's language (the app's, not English by
|
|
125
|
+
default):
|
|
126
|
+
|
|
127
|
+
- **Why and when** — one short paragraph: what this is for, and when the reader
|
|
128
|
+
would reach for it. Never "This page documents…".
|
|
129
|
+
- **The steps** — a numbered list, each one an action in the words on the
|
|
130
|
+
screen: "Open **Patienten** and choose **Patient anlegen**." Name buttons and
|
|
131
|
+
fields exactly as they read.
|
|
132
|
+
- **What you see afterwards** — the state that means it worked.
|
|
133
|
+
- **What goes wrong** — the refusal, the empty state, the thing that looks
|
|
134
|
+
broken but is not. Every empty state a scenario lands in and every
|
|
135
|
+
`expectError` in the feature is a candidate; this is usually the paragraph
|
|
136
|
+
readers came for.
|
|
137
|
+
- **Where next** — links to the pages a reader goes to from here.
|
|
138
|
+
|
|
139
|
+
Then the marker, after the steps it shows.
|
|
140
|
+
|
|
141
|
+
A page that exists only to cite a feature — "every page loads", "acceptance",
|
|
142
|
+
a smoke suite — is not a page. Cite that feature from the page whose screens it
|
|
143
|
+
covers, or mark it `document: false`.
|
|
144
|
+
|
|
145
|
+
Reassurance is content: "Codes held in reserve cost nothing until a patient
|
|
146
|
+
uses one" is what stops a reader hesitating over the button. Explain the
|
|
147
|
+
confusing thing, not the impressive one.
|
|
148
|
+
|
|
149
|
+
## 3. Every feature is accounted for
|
|
150
|
+
|
|
151
|
+
Every registered feature must be cited by some page. An uncited feature fails
|
|
152
|
+
the command by name:
|
|
153
|
+
|
|
154
|
+
```
|
|
155
|
+
Feature 'barFeature' is cited by no page. Place `<!-- pikku:guide feature=barFeature -->` …
|
|
156
|
+
```
|
|
157
|
+
|
|
158
|
+
Two ways out, both deliberate:
|
|
159
|
+
|
|
160
|
+
- Write the page. This is the normal answer.
|
|
161
|
+
- The feature is plumbing nobody reads about (a session-health check, an
|
|
162
|
+
internal sync): `pikkuFeature({ …, document: false })`. Citing a
|
|
163
|
+
`document: false` feature is itself an error.
|
|
164
|
+
|
|
165
|
+
`--allow-undocumented` downgrades the uncited-feature error to a warning, for a
|
|
166
|
+
guide that is mid-way through being written. Do not hand one over with it on.
|
|
167
|
+
|
|
168
|
+
A page citing an id that is not a registered feature is always an error — it
|
|
169
|
+
describes something that no longer exists.
|
|
170
|
+
|
|
171
|
+
## 4. Screenshots come from a capture step
|
|
172
|
+
|
|
173
|
+
The run only files screenshots a step asks for. Add one browser step that opens
|
|
174
|
+
a page and takes a shot, and call it from a scenario each feature owns:
|
|
175
|
+
|
|
176
|
+
```ts snippet:guideCaptureStep
|
|
177
|
+
```
|
|
178
|
+
|
|
179
|
+
- The screenshot `name` is the figure caption. Write it as a caption: "the
|
|
180
|
+
course list, with places left on each ticket".
|
|
181
|
+
- `{ showcase: true }` marks a shot fit to publish outside the run. `{ fullPage:
|
|
182
|
+
true }` photographs the whole scrollable page.
|
|
183
|
+
- Contexts open at a pinned 1440×900 viewport with animations off, so two runs
|
|
184
|
+
photograph the same thing. Override with `E2E_VIEWPORT_WIDTH` /
|
|
185
|
+
`E2E_VIEWPORT_HEIGHT` or the playwright config, or call
|
|
186
|
+
`page.setViewportSize` inside the step for a phone-width shot.
|
|
187
|
+
- Prefer a shot at the end of a real flow step (after the booking succeeds) over
|
|
188
|
+
a standalone "open and photograph" scenario — the figure then shows the state
|
|
189
|
+
the section describes.
|
|
190
|
+
|
|
191
|
+
### Traps that make a block come out empty
|
|
192
|
+
|
|
193
|
+
- **A feature whose scenarios are RPC-only files no screenshot.** The command
|
|
194
|
+
warns `whose run filed no screenshot — the block renders empty`. Fold that
|
|
195
|
+
scenario into a feature that has browser coverage, or add a browser capture
|
|
196
|
+
to it; do not invent a page just to photograph.
|
|
197
|
+
- **A capture loop must iterate a named const.** `for (const s of [ … ])` with
|
|
198
|
+
an inline array literal cannot be extracted (PKU679) and the scenario becomes
|
|
199
|
+
silently empty. `const screens = [ … ] as const` then `for (const s of screens)`.
|
|
200
|
+
- **A closing assertion runs wherever the last capture left the browser.**
|
|
201
|
+
Captures appended to the end of a scenario move the page out from under a
|
|
202
|
+
`then` that follows them. Capture after the last assertion, or re-navigate.
|
|
203
|
+
- **Locale.** Playwright reports `navigator.language` as `en-US`. An app that
|
|
204
|
+
picks its locale from the browser renders English, and every copy assertion
|
|
205
|
+
in another language fails. Set the app's own stored locale with
|
|
206
|
+
`page.addInitScript` in **every** step that navigates, not only the first.
|
|
207
|
+
|
|
208
|
+
## 5. Build it
|
|
209
|
+
|
|
210
|
+
```sh
|
|
211
|
+
# 1. a full, passing browser run that writes the shots to disk
|
|
212
|
+
bunx --bun pikku scenario run local --run browser --screenshots
|
|
213
|
+
|
|
214
|
+
# 2. merge prose + evidence → .pikku/guide/
|
|
215
|
+
bunx --bun pikku scenario guide --docs docs
|
|
216
|
+
```
|
|
217
|
+
|
|
218
|
+
- `--screenshots` is what writes files. Without it `browser.screenshot()`
|
|
219
|
+
still returns bytes and nothing lands on disk, so every block is empty.
|
|
220
|
+
- The run must have **passed**. A failed or killed run is refused — a page is a
|
|
221
|
+
claim that the product does what it says.
|
|
222
|
+
- The run must be **the whole suite**. A run narrowed with `--flows`,
|
|
223
|
+
`--features`, `--tags` or `--exclude-tags` is refused, because pages built
|
|
224
|
+
from it would describe missing flows as though they did not exist. An
|
|
225
|
+
exclusion that matches nothing still counts — keep every narrowing flag out
|
|
226
|
+
of a CI invocation whose run feeds the guide. `--run-id <id>` picks an older
|
|
227
|
+
full run.
|
|
228
|
+
|
|
229
|
+
## 6. `.guide.lock` — keeping prose honest
|
|
230
|
+
|
|
231
|
+
`docs/.guide.lock` records, per feature, a hash of its scenarios' **step
|
|
232
|
+
sentences and artifact ids** — deliberately not the image bytes. Restyling the
|
|
233
|
+
UI changes every screenshot and no sentence, so it does not stale a page.
|
|
234
|
+
Inserting, renaming or reordering a step changes what the prose around the
|
|
235
|
+
block was describing, and the page is reported:
|
|
236
|
+
|
|
237
|
+
```
|
|
238
|
+
docs/using/booking.md was written against 'bookingsFeature' at 3f1a…, which is now 9c0e… — the flow moved, so re-read the prose around that block.
|
|
239
|
+
```
|
|
240
|
+
|
|
241
|
+
Re-read that page's hand-written text, fix what the flow change made untrue,
|
|
242
|
+
and rebuild. The lock is rewritten on every successful build.
|
|
243
|
+
|
|
244
|
+
- **Commit the lock.** It is generated, never hand-edited, never hand-merged. A
|
|
245
|
+
tree whose lock is untracked reports every page as current forever.
|
|
246
|
+
- The first build after adding pages prints stale warnings for every feature
|
|
247
|
+
(there was no lock); they clear on the second build.
|
|
248
|
+
|
|
249
|
+
## 7. Hand-over checklist
|
|
250
|
+
|
|
251
|
+
- [ ] Every feature is cited, or declares `document: false` with a reason.
|
|
252
|
+
- [ ] No `--allow-undocumented` in the command you report as done.
|
|
253
|
+
- [ ] Built from a full, passing `--run browser --screenshots` run.
|
|
254
|
+
- [ ] No "block renders empty" warnings.
|
|
255
|
+
- [ ] No stale warnings left after the second build.
|
|
256
|
+
- [ ] `docs/` pages and `docs/.guide.lock` committed; `.pikku/guide/` is output.
|
|
257
|
+
- [ ] Every page reads as instructions with its figures removed: why and when,
|
|
258
|
+
numbered steps naming the controls as they read on screen, what goes
|
|
259
|
+
wrong.
|
|
260
|
+
- [ ] No page exists only to cite a smoke or acceptance feature.
|
|
261
|
+
- [ ] Scenario titles and screenshot names read as captions — no routes,
|
|
262
|
+
viewport sizes or test ids.
|
|
263
|
+
- [ ] Open two generated pages and look at them: the figures are the screens the
|
|
264
|
+
text describes, in the app's language.
|
|
@@ -24,7 +24,7 @@ Use this skill as an execution checklist, not reference material.
|
|
|
24
24
|
1. Discover before editing. Run the relevant `pikku meta ... --json` command and inspect only the focused output you need.
|
|
25
25
|
2. Identify the source files that own the behavior. Do not start by reading generated output, `.pikku`, `node_modules`, vendored packages, or broad build artifacts.
|
|
26
26
|
3. Make the smallest source change that satisfies the task. Keep generated files generated, and avoid hand-editing SDKs, schema output, or typegen.
|
|
27
|
-
4. Validate with the narrowest relevant command first, then run `pikku
|
|
27
|
+
4. Validate with the narrowest relevant command first, then run `pikku all` when functions, wirings, schemas, or generated clients may have changed.
|
|
28
28
|
5. If validation fails, fix the source cause and rerun validation. Do not paper over generated errors by editing generated files.
|
|
29
29
|
|
|
30
30
|
## Writing Queries — the Kysely query builder
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
name: pikku-n8n-import
|
|
3
3
|
description: 'Use to import an n8n workflow JSON export into a runnable Pikku workflow. Triggers when the user says "import this n8n workflow", "convert this n8n export to pikku", points at an n8n `.json` export or a directory of them, or picks up after `pikku import n8n` left throwing stub functions (`STUB — generated from n8n …`, `— implement me`) or a `<workflow>.integrations.json` manifest. Owns the whole flow: run the importer, triage what it could not map, fill each stub, report any missing `@pikku/addon-*` integrations, and verify the result compiles and runs with no surviving stubs. DO NOT TRIGGER for hand-written addon wiring unrelated to an n8n import (use pikku-addon), or for authoring workflows from scratch (use pikku-workflow).'
|
|
4
|
+
installGroups: [core]
|
|
4
5
|
metadata:
|
|
5
6
|
version: 1.0.0
|
|
6
7
|
---
|
|
@@ -19,14 +20,14 @@ missing dependency).
|
|
|
19
20
|
|
|
20
21
|
## Agent Operating Procedure
|
|
21
22
|
|
|
22
|
-
1. Discover before editing. Prefer `pikku
|
|
23
|
+
1. Discover before editing. Prefer `pikku meta ... --json` when
|
|
23
24
|
available; inspect only the focused output you need.
|
|
24
25
|
2. Identify the source file that owns the behavior. Do not start from generated
|
|
25
26
|
output, `.pikku`, `node_modules`, or vendored packages.
|
|
26
27
|
3. Make the smallest source change that satisfies the task. Keep generated files
|
|
27
28
|
generated.
|
|
28
|
-
4. Validate with the narrowest relevant command first, then `pikku all`
|
|
29
|
-
|
|
29
|
+
4. Validate with the narrowest relevant command first, then `pikku all` when
|
|
30
|
+
functions, wirings, or schemas changed.
|
|
30
31
|
5. If validation fails, fix the source cause and rerun. Never edit generated
|
|
31
32
|
files to hide an error.
|
|
32
33
|
|
|
@@ -1,6 +1,18 @@
|
|
|
1
1
|
# Pikku React
|
|
2
2
|
|
|
3
3
|
|
|
4
|
+
What is here:
|
|
5
|
+
|
|
6
|
+
- [What ships](#what-ships)
|
|
7
|
+
- [Resolving the server URL](#resolving-the-server-url)
|
|
8
|
+
- [Setup at the app root](#setup-at-the-app-root)
|
|
9
|
+
- [Calling an RPC directly (no React Query)](#calling-an-rpc-directly-no-react-query)
|
|
10
|
+
- [Calling fetch directly](#calling-fetch-directly)
|
|
11
|
+
- [Realtime subscriptions](#realtime-subscriptions)
|
|
12
|
+
- [When to reach for what](#when-to-reach-for-what)
|
|
13
|
+
- [Authentication](#authentication)
|
|
14
|
+
- [What NOT to do](#what-not-to-do)
|
|
15
|
+
|
|
4
16
|
## What ships
|
|
5
17
|
|
|
6
18
|
```tsx
|
|
@@ -3,17 +3,17 @@ name: pikku-realtime
|
|
|
3
3
|
description: >-
|
|
4
4
|
Use when making ANY view live/realtime in a Pikku app — a board, shared list, dashboard, ticker, bidding room, live count — or when adding two-way chat/presence. Covers the DEFAULT event-hub SSE path and the two-way WebSocket channel.
|
|
5
5
|
TRIGGER when: the user wants live updates, realtime, "update without refresh", a live board/feed/ticker/room, presence, or chat; or when data that MORE THAN ONE signed-in user can change should reflect others
|
|
6
|
-
DO NOT TRIGGER when: a plain one-shot query/refetch is fine (data only one user changes, or a manual refresh is acceptable), or for background jobs (
|
|
6
|
+
DO NOT TRIGGER when: a plain one-shot query/refetch is fine (data only one user changes, or a manual refresh is acceptable), or for background jobs (see `pikku-wiring`'s scheduler and queue references, or `pikku-workflow`).
|
|
7
7
|
installGroups: [core, client]
|
|
8
8
|
---
|
|
9
9
|
|
|
10
10
|
# Pikku Realtime (SSE + WebSocket channels)
|
|
11
11
|
|
|
12
|
-
There is NOTHING to hand-roll and NOTHING to "find".
|
|
13
|
-
|
|
14
|
-
templates. Start from them and rename — never grep the
|
|
15
|
-
`sse`/`eventHub` code to copy, never write a custom
|
|
16
|
-
write a bespoke `sse: true` route for a plain live feed.
|
|
12
|
+
There is NOTHING to hand-roll and NOTHING to "find". `pikku enable events` wires
|
|
13
|
+
the event-hub SSE transport and generates the typed client, and the two patterns
|
|
14
|
+
below ARE the realtime templates. Start from them and rename — never grep the
|
|
15
|
+
project for existing `sse`/`eventHub` code to copy, never write a custom
|
|
16
|
+
`EventSource`, and never write a bespoke `sse: true` route for a plain live feed.
|
|
17
17
|
|
|
18
18
|
## Pick the transport (almost always SSE)
|
|
19
19
|
|
|
@@ -0,0 +1,143 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: pikku-report
|
|
3
|
+
description: >-
|
|
4
|
+
Use when pikku itself cost you time — wrong generated types, a check that passes when it
|
|
5
|
+
should not, output that is quietly wrong, a skill that misled you — or when the user asks you
|
|
6
|
+
to report a framework bug, file a finding, or look at what is queued. Owns `pikku fabric
|
|
7
|
+
report` (a finding is about pikku, not the app), the product-vs-harness kinds, the
|
|
8
|
+
workaround-first ladder, and the local findings spool. TRIGGER when: the framework fought you,
|
|
9
|
+
codegen produced something broken, a skill told you to run something that does not exist, the
|
|
10
|
+
user says "report this to pikku" / "file a finding" / "check the findings queue", or a finding
|
|
11
|
+
was queued and never sent. DO NOT TRIGGER when: the bug is in the app you are building (fix it
|
|
12
|
+
there), or you are tempted to patch pikku's source (never do that from an app).
|
|
13
|
+
installGroups: [core]
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
# Report a finding to Fabric
|
|
17
|
+
|
|
18
|
+
A finding is about **pikku**, not about the app you are building. It is how the
|
|
19
|
+
framework learns what cost its users time — the bug, the misleading skill, the
|
|
20
|
+
silence where a check should have complained.
|
|
21
|
+
|
|
22
|
+
Nothing is written to the repository. The terminal receipt shows exactly what
|
|
23
|
+
left your machine, and the command is spelled `pikku fabric report` — there is
|
|
24
|
+
no top-level report command.
|
|
25
|
+
|
|
26
|
+
## Report at the moment it happens
|
|
27
|
+
|
|
28
|
+
Not at the end from memory: a run that falls over never reaches its end, and the
|
|
29
|
+
mechanism is already loaded while you are in it. One finding per thing that
|
|
30
|
+
fought you.
|
|
31
|
+
|
|
32
|
+
The ladder decides how much to spend:
|
|
33
|
+
|
|
34
|
+
1. **Find the quicker workaround.** The user is paying for their feature, not
|
|
35
|
+
for pikku's health.
|
|
36
|
+
2. **Investigate** only when there is no workaround, or when the user asks why
|
|
37
|
+
something is slow or wrong.
|
|
38
|
+
3. **Report at the depth you already reached.** Never spend extra effort to
|
|
39
|
+
file; never throw away effort you already spent. If the investigation took
|
|
40
|
+
you to the mechanism, the finding says so — named file, named function, what
|
|
41
|
+
is actually happening, and what pikku should do instead.
|
|
42
|
+
|
|
43
|
+
## What counts
|
|
44
|
+
|
|
45
|
+
Anything that cost you time and would cost the next person the same. Most of
|
|
46
|
+
these never produce an error: output that is quietly wrong, a generated type
|
|
47
|
+
that disagrees with the runtime, a check that passes when it should not, a
|
|
48
|
+
narrowing you had to write by hand because the framework should have written
|
|
49
|
+
it. **Having to write code the framework should have written for you is a
|
|
50
|
+
finding.**
|
|
51
|
+
|
|
52
|
+
Also anything that only shows up in one place — invisible locally, fatal
|
|
53
|
+
deployed, or the reverse. Say which with `--surface local|deployed|both`.
|
|
54
|
+
|
|
55
|
+
Not a finding: a preference, a thing you would have designed differently, or
|
|
56
|
+
baseline noise that was already failing before you started.
|
|
57
|
+
|
|
58
|
+
## Two kinds
|
|
59
|
+
|
|
60
|
+
- `--kind product` — pikku behaved wrongly. Fixing it is a change to the
|
|
61
|
+
framework.
|
|
62
|
+
- `--kind harness` — a skill misled you: it told you to run something that does
|
|
63
|
+
not exist, described a flag that is spelled differently, or contradicted what
|
|
64
|
+
the CLI actually did. Pass `--skill <name>` and `--passage "<the line or
|
|
65
|
+
section>"`. This is the most useful kind to file, because it is fixable
|
|
66
|
+
immediately — so file it even when the cost was small.
|
|
67
|
+
|
|
68
|
+
## The command
|
|
69
|
+
|
|
70
|
+
Send it as JSON on stdin. Most of a finding is prose, and prose carries
|
|
71
|
+
apostrophes, quotes, backticks and newlines — each one a shell metacharacter
|
|
72
|
+
before it is a character in your sentence. A stack trace passed to `--error`
|
|
73
|
+
breaks the command at its first newline; a backtick in `--actual` runs whatever
|
|
74
|
+
follows it. Quote the heredoc delimiter (`<<'EOF'`, never `<<EOF`) so the shell
|
|
75
|
+
leaves the body alone.
|
|
76
|
+
|
|
77
|
+
```bash
|
|
78
|
+
pikku fabric report --stdin <<'EOF'
|
|
79
|
+
{
|
|
80
|
+
"title": "<one-line title>",
|
|
81
|
+
"kind": "product",
|
|
82
|
+
"model": "<the model you are>",
|
|
83
|
+
"expected": "<what you expected pikku to do>",
|
|
84
|
+
"actual": "<what it did instead>",
|
|
85
|
+
"command": "<the command you ran>",
|
|
86
|
+
"workaround": "<what you did instead, inside the app>"
|
|
87
|
+
}
|
|
88
|
+
EOF
|
|
89
|
+
```
|
|
90
|
+
|
|
91
|
+
The same fields exist as flags for a finding short enough to type; `pikku fabric
|
|
92
|
+
report --help` lists them. Whichever path you use, the rules below are checked
|
|
93
|
+
before anything is sent:
|
|
94
|
+
|
|
95
|
+
- `kind` is `product` or `harness`, and a `harness` finding names the skill that
|
|
96
|
+
misled you.
|
|
97
|
+
- A resolved finding carries the `workaround` you used (or a `proposal`).
|
|
98
|
+
- `--unresolved` means **no workaround was found** — it requires `--tried` with
|
|
99
|
+
what you attempted and how each attempt failed, and it forbids `--workaround`.
|
|
100
|
+
It does not mean the workaround was unpleasant.
|
|
101
|
+
|
|
102
|
+
Add whichever of these you actually have: `error` (the error's message line,
|
|
103
|
+
verbatim), `repro` (the shortest way to reach it again), `proposal`, `area`,
|
|
104
|
+
`surface`, `cost` (measured if you measured it — "98s vs 20s steady" ranks;
|
|
105
|
+
"slow" does not), `run` (an id shared by every finding from this build),
|
|
106
|
+
`deployTarget`.
|
|
107
|
+
|
|
108
|
+
Versions, platform and package manager are read off the installed tree for you.
|
|
109
|
+
Do not pass them and do not ask the user for them.
|
|
110
|
+
|
|
111
|
+
## When it cannot send
|
|
112
|
+
|
|
113
|
+
Reporting never fails a build. A finding that cannot be sent — logged out, or
|
|
114
|
+
fabric unreachable — is held on the machine and goes out with the next report
|
|
115
|
+
that succeeds, so nothing you file is lost:
|
|
116
|
+
|
|
117
|
+
- `pikku fabric findings list` shows what is queued.
|
|
118
|
+
- `pikku fabric findings flush` sends everything queued.
|
|
119
|
+
- `pikku fabric findings clear` discards it.
|
|
120
|
+
|
|
121
|
+
If the terminal says the finding was queued, carry on with what you were doing.
|
|
122
|
+
Do not try to fix the send, and do not file the same thing again.
|
|
123
|
+
|
|
124
|
+
## Never fix pikku itself
|
|
125
|
+
|
|
126
|
+
Not a patch in `node_modules`, not a linked checkout, not a branch in the
|
|
127
|
+
framework repo. Many agents each patching pikku to unblock themselves is many
|
|
128
|
+
divergent copies and a merge problem nobody signed up for. Work around it in the
|
|
129
|
+
app, report it, and let the fix happen once.
|
|
130
|
+
|
|
131
|
+
## What NOT to do
|
|
132
|
+
|
|
133
|
+
- **Do not report a bug in the app as a pikku finding.** If the app's own code
|
|
134
|
+
is wrong, fix it; a finding that turns out to be the caller's mistake costs
|
|
135
|
+
the maintainers more than it cost you.
|
|
136
|
+
- **Do not batch findings at the end of a build.** You will have lost the
|
|
137
|
+
mechanism and the command, and the report wins nothing.
|
|
138
|
+
- **Do not file without a workaround or an `--unresolved --tried`.** A finding
|
|
139
|
+
that cannot be acted on is noise.
|
|
140
|
+
- **Do not paste a secret, token or customer data into a finding.** The payload
|
|
141
|
+
leaves your machine; keep it to the mechanism.
|
|
142
|
+
- **Do not ask the user for versions or platform.** They are collected
|
|
143
|
+
automatically.
|