retold 4.0.1 → 4.0.2
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/.claude/settings.local.json +27 -1
- package/docs/README.md +7 -6
- package/docs/_sidebar.md +34 -21
- package/docs/_topbar.md +2 -2
- package/docs/architecture/module-architecture.md +234 -0
- package/docs/{modules.md → architecture/modules.md} +25 -22
- package/docs/cover.md +2 -2
- package/docs/css/docuserve.css +6 -6
- package/docs/examples/examples.md +71 -0
- package/docs/examples/todolist/todo-list-cli-client.md +178 -0
- package/docs/examples/todolist/todo-list-console-client.md +152 -0
- package/docs/examples/todolist/todo-list-model.md +114 -0
- package/docs/examples/todolist/todo-list-server.md +128 -0
- package/docs/examples/todolist/todo-list-web-client.md +177 -0
- package/docs/examples/todolist/todo-list.md +162 -0
- package/docs/getting-started.md +8 -7
- package/docs/index.html +4 -4
- package/docs/{meadow.md → modules/meadow.md} +4 -6
- package/docs/{orator.md → modules/orator.md} +1 -0
- package/docs/{pict.md → modules/pict.md} +30 -8
- package/docs/{utility.md → modules/utility.md} +0 -9
- package/docs/retold-catalog.json +896 -2317
- package/docs/retold-keyword-index.json +162327 -120227
- package/examples/todo-list/Dockerfile +45 -0
- package/examples/todo-list/README.md +394 -0
- package/examples/todo-list/cli-client/package-lock.json +418 -0
- package/examples/todo-list/cli-client/package.json +19 -0
- package/examples/todo-list/cli-client/source/TodoCLI-CLIProgram.js +30 -0
- package/examples/todo-list/cli-client/source/TodoCLI-Run.js +3 -0
- package/examples/todo-list/cli-client/source/commands/add/TodoCLI-Command-Add.js +74 -0
- package/examples/todo-list/cli-client/source/commands/complete/TodoCLI-Command-Complete.js +84 -0
- package/examples/todo-list/cli-client/source/commands/list/TodoCLI-Command-List.js +110 -0
- package/examples/todo-list/cli-client/source/commands/remove/TodoCLI-Command-Remove.js +49 -0
- package/examples/todo-list/cli-client/source/services/TodoCLI-Service-API.js +92 -0
- package/examples/todo-list/console-client/console-client.cjs +913 -0
- package/examples/todo-list/console-client/package-lock.json +426 -0
- package/examples/todo-list/console-client/package.json +19 -0
- package/examples/todo-list/console-client/views/PictView-TUI-Header.cjs +43 -0
- package/examples/todo-list/console-client/views/PictView-TUI-Layout.cjs +58 -0
- package/examples/todo-list/console-client/views/PictView-TUI-StatusBar.cjs +41 -0
- package/examples/todo-list/console-client/views/PictView-TUI-TaskList.cjs +104 -0
- package/examples/todo-list/docker-motd.sh +36 -0
- package/examples/todo-list/docker-run.sh +2 -0
- package/examples/todo-list/docker-shell.sh +2 -0
- package/examples/todo-list/model/MeadowSchema-Task.json +152 -0
- package/examples/todo-list/model/Task-Compiled.json +25 -0
- package/examples/todo-list/model/Task.mddl +15 -0
- package/examples/todo-list/model/data/seeded_todo_events.csv +1001 -0
- package/examples/todo-list/server/database-initialization-service.cjs +273 -0
- package/examples/todo-list/server/package-lock.json +6113 -0
- package/examples/todo-list/server/package.json +19 -0
- package/examples/todo-list/server/server.cjs +138 -0
- package/examples/todo-list/web-client/css/todolist-theme.css +235 -0
- package/examples/todo-list/web-client/generate-build-config.cjs +18 -0
- package/examples/todo-list/web-client/html/index.html +18 -0
- package/examples/todo-list/web-client/package-lock.json +12030 -0
- package/examples/todo-list/web-client/package.json +43 -0
- package/examples/todo-list/web-client/source/TodoList-Application-Config.json +12 -0
- package/examples/todo-list/web-client/source/TodoList-Application.cjs +383 -0
- package/examples/todo-list/web-client/source/providers/Provider-TaskData.cjs +243 -0
- package/examples/todo-list/web-client/source/providers/Router-Config.json +32 -0
- package/examples/todo-list/web-client/source/views/View-Layout.cjs +75 -0
- package/examples/todo-list/web-client/source/views/View-TaskForm.cjs +87 -0
- package/examples/todo-list/web-client/source/views/View-TaskList.cjs +127 -0
- package/examples/todo-list/web-client/source/views/calendar/View-MonthView.cjs +293 -0
- package/examples/todo-list/web-client/source/views/calendar/View-WeekView.cjs +149 -0
- package/examples/todo-list/web-client/source/views/calendar/View-YearView.cjs +226 -0
- package/modules/Include-Retold-Module-List.sh +2 -2
- package/package.json +5 -5
- package/docs/js/pict.min.js +0 -12
- package/docs/js/pict.min.js.map +0 -1
- package/docs/pict-docuserve.min.js +0 -58
- package/docs/pict-docuserve.min.js.map +0 -1
- /package/docs/{architecture.md → architecture/architecture.md} +0 -0
- /package/docs/{fable.md → modules/fable.md} +0 -0
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
FROM node:20-slim
|
|
2
|
+
|
|
3
|
+
LABEL maintainer="Retold <https://github.com/stevenvelozo/retold>"
|
|
4
|
+
LABEL description="Retold Todo List Example -- API Server, Web Client, CLI, and Console TUI"
|
|
5
|
+
|
|
6
|
+
WORKDIR /app
|
|
7
|
+
|
|
8
|
+
# Copy the shared data model
|
|
9
|
+
COPY model/ model/
|
|
10
|
+
|
|
11
|
+
# --- Server ---
|
|
12
|
+
COPY server/package.json server/package.json
|
|
13
|
+
COPY server/server.cjs server/server.cjs
|
|
14
|
+
COPY server/database-initialization-service.cjs server/database-initialization-service.cjs
|
|
15
|
+
RUN mkdir -p server/data
|
|
16
|
+
RUN cd server && npm install --omit=dev
|
|
17
|
+
|
|
18
|
+
# --- Web Client ---
|
|
19
|
+
COPY web-client/package.json web-client/package.json
|
|
20
|
+
COPY web-client/generate-build-config.cjs web-client/generate-build-config.cjs
|
|
21
|
+
COPY web-client/.gulpfile-quackage.js web-client/.gulpfile-quackage.js
|
|
22
|
+
COPY web-client/source/ web-client/source/
|
|
23
|
+
COPY web-client/html/ web-client/html/
|
|
24
|
+
COPY web-client/css/ web-client/css/
|
|
25
|
+
RUN cd web-client && npm install
|
|
26
|
+
RUN cd web-client && npm run build
|
|
27
|
+
|
|
28
|
+
# --- CLI Client ---
|
|
29
|
+
COPY cli-client/package.json cli-client/package.json
|
|
30
|
+
COPY cli-client/source/ cli-client/source/
|
|
31
|
+
RUN cd cli-client && npm install --omit=dev
|
|
32
|
+
|
|
33
|
+
# --- Console Client ---
|
|
34
|
+
COPY console-client/package.json console-client/package.json
|
|
35
|
+
COPY console-client/console-client.cjs console-client/console-client.cjs
|
|
36
|
+
COPY console-client/views/ console-client/views/
|
|
37
|
+
RUN cd console-client && npm install --omit=dev
|
|
38
|
+
|
|
39
|
+
# --- Help message shown on interactive login ---
|
|
40
|
+
COPY docker-motd.sh /etc/profile.d/motd.sh
|
|
41
|
+
|
|
42
|
+
EXPOSE 8086
|
|
43
|
+
|
|
44
|
+
# Default: start the API server (serves the web client too)
|
|
45
|
+
CMD ["node", "server/server.cjs"]
|
|
@@ -0,0 +1,394 @@
|
|
|
1
|
+
# Retold Todo List Example
|
|
2
|
+
|
|
3
|
+
A complete example demonstrating the full Retold stack: an API server with
|
|
4
|
+
Meadow endpoints, a Pict web client, a blessed console client, and a
|
|
5
|
+
command-line utility -- all connected to the same SQLite backend through a
|
|
6
|
+
shared REST API.
|
|
7
|
+
|
|
8
|
+
## Architecture
|
|
9
|
+
|
|
10
|
+
```mermaid
|
|
11
|
+
graph TB
|
|
12
|
+
subgraph model["Shared Data Model"]
|
|
13
|
+
mddl["Task.mddl<br/><i>Stricture MicroDDL</i>"]
|
|
14
|
+
compiled["Task-Compiled.json<br/><i>DDL for table creation</i>"]
|
|
15
|
+
schema["MeadowSchema-Task.json<br/><i>ORM schema, types, defaults</i>"]
|
|
16
|
+
csv["seeded_todo_events.csv<br/><i>1,000 sample tasks</i>"]
|
|
17
|
+
mddl --> compiled
|
|
18
|
+
mddl --> schema
|
|
19
|
+
end
|
|
20
|
+
|
|
21
|
+
subgraph server["API Server  ·  Orator + Meadow + SQLite"]
|
|
22
|
+
orator["Orator<br/><i>HTTP server (Restify)</i>"]
|
|
23
|
+
endpoints["Meadow Endpoints<br/><i>Auto-generated REST CRUD</i>"]
|
|
24
|
+
dal["Meadow DAL<br/><i>Task entity ORM</i>"]
|
|
25
|
+
dbinit["DatabaseInitializationService<br/><i>Table creation & CSV seeding</i>"]
|
|
26
|
+
sqlite[("todo.sqlite")]
|
|
27
|
+
static["Static file server<br/><i>Serves web-client/dist/</i>"]
|
|
28
|
+
|
|
29
|
+
orator --- endpoints
|
|
30
|
+
endpoints --- dal
|
|
31
|
+
dal --- sqlite
|
|
32
|
+
dbinit --> dal
|
|
33
|
+
orator --- static
|
|
34
|
+
end
|
|
35
|
+
|
|
36
|
+
compiled --> dbinit
|
|
37
|
+
schema --> dal
|
|
38
|
+
csv --> dbinit
|
|
39
|
+
|
|
40
|
+
subgraph web["Web Client  ·  Pict Application"]
|
|
41
|
+
wapp["TodoList-Application<br/><i>Lifecycle, routing, state</i>"]
|
|
42
|
+
wprov["Provider-TaskData<br/><i>API fetch, query builder</i>"]
|
|
43
|
+
wrouter["PictRouter<br/><i>Hash-based SPA routing</i>"]
|
|
44
|
+
|
|
45
|
+
subgraph wviews["Views"]
|
|
46
|
+
wlayout["View-Layout<br/><i>Nav bar + content outlet</i>"]
|
|
47
|
+
wlist["View-TaskList<br/><i>Sortable table, search, pagination</i>"]
|
|
48
|
+
wform["View-TaskForm<br/><i>Add / edit task form</i>"]
|
|
49
|
+
wweek["View-WeekView<br/><i>Week calendar grid</i>"]
|
|
50
|
+
wmonth["View-MonthView<br/><i>Month calendar grid</i>"]
|
|
51
|
+
wyear["View-YearView<br/><i>Year overview cards + table</i>"]
|
|
52
|
+
end
|
|
53
|
+
|
|
54
|
+
wapp --- wprov
|
|
55
|
+
wapp --- wrouter
|
|
56
|
+
wapp --- wlayout
|
|
57
|
+
wlayout --- wlist
|
|
58
|
+
wlayout --- wform
|
|
59
|
+
wlayout --- wweek
|
|
60
|
+
wlayout --- wmonth
|
|
61
|
+
wlayout --- wyear
|
|
62
|
+
end
|
|
63
|
+
|
|
64
|
+
subgraph console["Console Client  ·  blessed TUI"]
|
|
65
|
+
capp["TodoListConsoleApplication<br/><i>Screen, widgets, key bindings</i>"]
|
|
66
|
+
ctui["pict-terminalui<br/><i>Pict → blessed bridge</i>"]
|
|
67
|
+
|
|
68
|
+
subgraph cviews["Views"]
|
|
69
|
+
clayout["TUI-Layout<br/><i>Header / content / status</i>"]
|
|
70
|
+
cheader["TUI-Header<br/><i>Title + keybinding bar</i>"]
|
|
71
|
+
clist["TUI-TaskList<br/><i>Scrollable task rows</i>"]
|
|
72
|
+
cstatus["TUI-StatusBar<br/><i>Count, sort, status message</i>"]
|
|
73
|
+
end
|
|
74
|
+
|
|
75
|
+
subgraph cmodals["Modals"]
|
|
76
|
+
cview["View Detail<br/><i>Read-only task info</i>"]
|
|
77
|
+
cedit["Edit / Add<br/><i>Sequential field prompts</i>"]
|
|
78
|
+
csort["Sort Picker<br/><i>10 sort options</i>"]
|
|
79
|
+
csearch["Search<br/><i>Name + description filter</i>"]
|
|
80
|
+
end
|
|
81
|
+
|
|
82
|
+
capp --- ctui
|
|
83
|
+
ctui --- clayout
|
|
84
|
+
clayout --- cheader
|
|
85
|
+
clayout --- clist
|
|
86
|
+
clayout --- cstatus
|
|
87
|
+
capp --- cview
|
|
88
|
+
capp --- cedit
|
|
89
|
+
capp --- csort
|
|
90
|
+
capp --- csearch
|
|
91
|
+
end
|
|
92
|
+
|
|
93
|
+
subgraph cli["CLI Client  ·  pict-service-commandlineutility"]
|
|
94
|
+
cliapp["TodoCLI-CLIProgram<br/><i>Commander.js bootstrap</i>"]
|
|
95
|
+
cliapi["TodoCLI-Service-API<br/><i>HTTP client + query builder</i>"]
|
|
96
|
+
|
|
97
|
+
subgraph clicmds["Commands"]
|
|
98
|
+
clilist["list<br/><i>Search, sort, filter, paginate</i>"]
|
|
99
|
+
cliadd["add<br/><i>Create a new task</i>"]
|
|
100
|
+
cliremove["remove<br/><i>Delete a task by ID</i>"]
|
|
101
|
+
clicomplete["complete<br/><i>Mark a task done</i>"]
|
|
102
|
+
end
|
|
103
|
+
|
|
104
|
+
cliapp --- cliapi
|
|
105
|
+
cliapp --- clilist
|
|
106
|
+
cliapp --- cliadd
|
|
107
|
+
cliapp --- cliremove
|
|
108
|
+
cliapp --- clicomplete
|
|
109
|
+
end
|
|
110
|
+
|
|
111
|
+
wprov -- "fetch()" --> orator
|
|
112
|
+
static -- "HTML + JS + CSS" --> web
|
|
113
|
+
capp -- "http.request()" --> orator
|
|
114
|
+
cliapi -- "http.request()" --> orator
|
|
115
|
+
```
|
|
116
|
+
|
|
117
|
+
## Quickstart
|
|
118
|
+
|
|
119
|
+
### Prerequisites
|
|
120
|
+
|
|
121
|
+
- Node.js 18+
|
|
122
|
+
|
|
123
|
+
### 1. Start the API Server
|
|
124
|
+
|
|
125
|
+
```bash
|
|
126
|
+
cd server
|
|
127
|
+
npm install
|
|
128
|
+
npm start
|
|
129
|
+
```
|
|
130
|
+
|
|
131
|
+
The server starts on **http://localhost:8086**. On first run it creates a
|
|
132
|
+
SQLite database at `server/data/todo.sqlite`, builds the Task table from the
|
|
133
|
+
compiled Stricture DDL, and seeds 1,000 sample tasks from the CSV through the
|
|
134
|
+
Meadow DAL (so every record gets a GUID, audit timestamps, and defaults
|
|
135
|
+
automatically).
|
|
136
|
+
|
|
137
|
+
Meadow Endpoints auto-generates the full REST API:
|
|
138
|
+
|
|
139
|
+
| Method | Endpoint | Description |
|
|
140
|
+
|--------|----------|-------------|
|
|
141
|
+
| GET | `/1.0/Tasks/0/50` | List tasks (paginated) |
|
|
142
|
+
| GET | `/1.0/Tasks/FilteredTo/{filter}/0/50` | List with sort, search, filter |
|
|
143
|
+
| GET | `/1.0/Task/:id` | Get a single task |
|
|
144
|
+
| POST | `/1.0/Task` | Create a task |
|
|
145
|
+
| PUT | `/1.0/Task` | Update a task |
|
|
146
|
+
| DELETE | `/1.0/Task/:id` | Delete a task |
|
|
147
|
+
| GET | `/1.0/Tasks/Count` | Record count |
|
|
148
|
+
|
|
149
|
+
### 2. Build and Open the Web Client
|
|
150
|
+
|
|
151
|
+
In a second terminal:
|
|
152
|
+
|
|
153
|
+
```bash
|
|
154
|
+
cd web-client
|
|
155
|
+
npm install
|
|
156
|
+
npm run build
|
|
157
|
+
```
|
|
158
|
+
|
|
159
|
+
Then open **http://localhost:8086** in your browser. The server serves the
|
|
160
|
+
built web client as static files.
|
|
161
|
+
|
|
162
|
+
The web client is a Pict Application with hash-based routing. It includes a
|
|
163
|
+
sortable task list with search and pagination, an add/edit form, and three
|
|
164
|
+
calendar views (week, month, year) -- all styled with the Sagebrush color
|
|
165
|
+
theme.
|
|
166
|
+
|
|
167
|
+
### 3. Run the Console Client
|
|
168
|
+
|
|
169
|
+
In a third terminal (server must be running):
|
|
170
|
+
|
|
171
|
+
```bash
|
|
172
|
+
cd console-client
|
|
173
|
+
npm install
|
|
174
|
+
npm start
|
|
175
|
+
```
|
|
176
|
+
|
|
177
|
+
A blessed terminal UI that connects to the same API. Navigate with arrow keys:
|
|
178
|
+
|
|
179
|
+
| Key | Action |
|
|
180
|
+
|-----|--------|
|
|
181
|
+
| Enter | View task detail |
|
|
182
|
+
| E | Edit selected task |
|
|
183
|
+
| A | Add a new task |
|
|
184
|
+
| D | Delete selected task |
|
|
185
|
+
| S | Open sort picker |
|
|
186
|
+
| / | Search by name or description |
|
|
187
|
+
| R | Refresh from server |
|
|
188
|
+
| Q | Quit |
|
|
189
|
+
|
|
190
|
+
### 4. Use the CLI Client
|
|
191
|
+
|
|
192
|
+
In any terminal (server must be running):
|
|
193
|
+
|
|
194
|
+
```bash
|
|
195
|
+
cd cli-client
|
|
196
|
+
npm install
|
|
197
|
+
```
|
|
198
|
+
|
|
199
|
+
Then use the `todo` command (via `node source/TodoCLI-Run.js` or `npx todo`
|
|
200
|
+
after install):
|
|
201
|
+
|
|
202
|
+
```bash
|
|
203
|
+
# List tasks (newest first, up to 50)
|
|
204
|
+
npx todo list
|
|
205
|
+
|
|
206
|
+
# List with options
|
|
207
|
+
npx todo list --search garden --limit 10
|
|
208
|
+
npx todo list --column Name --direction ASC
|
|
209
|
+
npx todo list --status Pending
|
|
210
|
+
|
|
211
|
+
# Add a task
|
|
212
|
+
npx todo add "Water the plants" --due 2026-03-15 --hours 0.5
|
|
213
|
+
|
|
214
|
+
# Mark a task complete
|
|
215
|
+
npx todo complete 42
|
|
216
|
+
|
|
217
|
+
# Remove a task
|
|
218
|
+
npx todo remove 42
|
|
219
|
+
|
|
220
|
+
# See all commands
|
|
221
|
+
npx todo --help
|
|
222
|
+
```
|
|
223
|
+
|
|
224
|
+
## Running with Docker
|
|
225
|
+
|
|
226
|
+
If you have Docker installed you can skip the per-component setup and run
|
|
227
|
+
everything in a container. The image installs all four components, builds the
|
|
228
|
+
web client, and seeds the database on first start.
|
|
229
|
+
|
|
230
|
+
### Quick Start (server only)
|
|
231
|
+
|
|
232
|
+
```bash
|
|
233
|
+
./docker-run.sh
|
|
234
|
+
```
|
|
235
|
+
|
|
236
|
+
This builds the image and starts the API server. Open **http://localhost:8086**
|
|
237
|
+
in your browser for the web client.
|
|
238
|
+
|
|
239
|
+
### Interactive Shell
|
|
240
|
+
|
|
241
|
+
```bash
|
|
242
|
+
./docker-shell.sh
|
|
243
|
+
```
|
|
244
|
+
|
|
245
|
+
This builds the image and drops you into a bash shell inside the container. A
|
|
246
|
+
help banner lists the available commands. To use the CLI or console client,
|
|
247
|
+
start the server in the background first:
|
|
248
|
+
|
|
249
|
+
```bash
|
|
250
|
+
node server/server.cjs &
|
|
251
|
+
cd /app/cli-client && npx todo list
|
|
252
|
+
```
|
|
253
|
+
|
|
254
|
+
Or launch the console TUI:
|
|
255
|
+
|
|
256
|
+
```bash
|
|
257
|
+
node server/server.cjs &
|
|
258
|
+
node console-client/console-client.cjs
|
|
259
|
+
```
|
|
260
|
+
|
|
261
|
+
## What Each Component Does
|
|
262
|
+
|
|
263
|
+
### Shared Data Model (`model/`)
|
|
264
|
+
|
|
265
|
+
The Task entity is defined once and shared by every component.
|
|
266
|
+
|
|
267
|
+
| File | Role |
|
|
268
|
+
|------|------|
|
|
269
|
+
| `Task.mddl` | Stricture MicroDDL source -- one-line-per-field schema notation |
|
|
270
|
+
| `Task-Compiled.json` | Compiled DDL consumed by the SQLite table creator |
|
|
271
|
+
| `MeadowSchema-Task.json` | Meadow ORM schema with column types, defaults, and JSON Schema |
|
|
272
|
+
| `data/seeded_todo_events.csv` | 1,000 realistic tasks spanning four years of family life |
|
|
273
|
+
|
|
274
|
+
### API Server (`server/`)
|
|
275
|
+
|
|
276
|
+
A thin orchestration layer -- most behavior comes from Retold modules.
|
|
277
|
+
|
|
278
|
+
| File | Role |
|
|
279
|
+
|------|------|
|
|
280
|
+
| `server.cjs` | Wires Fable, Orator, Meadow, and SQLite together. Loads the schema, creates the DAL, generates REST endpoints, and starts the HTTP server. Also serves static files from `web-client/dist/`. |
|
|
281
|
+
| `database-initialization-service.cjs` | Fable service that creates tables from compiled DDL and seeds data from CSV through the Meadow DAL on first run. |
|
|
282
|
+
|
|
283
|
+
### Web Client (`web-client/`)
|
|
284
|
+
|
|
285
|
+
A browser-based Pict Application built with Quackage.
|
|
286
|
+
|
|
287
|
+
| File | Role |
|
|
288
|
+
|------|------|
|
|
289
|
+
| `source/TodoList-Application.cjs` | Application class -- registers views, providers, and router. Manages shared state in `AppData.TodoList`. |
|
|
290
|
+
| `source/providers/Provider-TaskData.cjs` | Data provider that builds FilteredTo query URLs and fetches from the API. |
|
|
291
|
+
| `source/providers/Router-Config.json` | Route table mapping hash paths to views. |
|
|
292
|
+
| `source/views/View-Layout.cjs` | Root layout with Sagebrush-themed navigation bar and `#TodoList-Content` outlet. |
|
|
293
|
+
| `source/views/View-TaskList.cjs` | Paginated data table with sort dropdown, search bar, and per-row edit/delete actions. |
|
|
294
|
+
| `source/views/View-TaskForm.cjs` | Create/edit form with Name, Description, DueDate, Hours, and Status fields. |
|
|
295
|
+
| `source/views/calendar/View-WeekView.cjs` | Seven-day calendar grid with task counts per day. |
|
|
296
|
+
| `source/views/calendar/View-MonthView.cjs` | Full month grid with day cells showing complete/open counts. |
|
|
297
|
+
| `source/views/calendar/View-YearView.cjs` | Twelve month overview cards plus a summary table. |
|
|
298
|
+
| `css/todolist-theme.css` | Shared Sagebrush theme stylesheet (loaded via `<link>` in `index.html`). |
|
|
299
|
+
| `html/index.html` | HTML shell -- loads Pict, the application bundle, and the theme CSS. |
|
|
300
|
+
|
|
301
|
+
### Console Client (`console-client/`)
|
|
302
|
+
|
|
303
|
+
A terminal UI using blessed widgets, bridged to Pict views through pict-terminalui.
|
|
304
|
+
|
|
305
|
+
| File | Role |
|
|
306
|
+
|------|------|
|
|
307
|
+
| `console-client.cjs` | Application class with blessed screen setup, keyboard navigation, four modal dialogs (view, edit, sort, search), and HTTP client for API calls. |
|
|
308
|
+
| `views/PictView-TUI-Layout.cjs` | Root blessed layout (header + content + status bar). |
|
|
309
|
+
| `views/PictView-TUI-Header.cjs` | Title bar with keybinding reference. |
|
|
310
|
+
| `views/PictView-TUI-TaskList.cjs` | Scrollable task list rendered from AppData with selection highlighting. |
|
|
311
|
+
| `views/PictView-TUI-StatusBar.cjs` | Status line showing task count, status message, and current sort. |
|
|
312
|
+
|
|
313
|
+
### CLI Client (`cli-client/`)
|
|
314
|
+
|
|
315
|
+
A non-interactive command-line tool built on pict-service-commandlineutility (Commander.js + Fable service container).
|
|
316
|
+
|
|
317
|
+
| File | Role |
|
|
318
|
+
|------|------|
|
|
319
|
+
| `source/TodoCLI-Run.js` | Shebang entry point for the `todo` bin command. |
|
|
320
|
+
| `source/TodoCLI-CLIProgram.js` | Bootstrap -- registers commands and the API service. Configurable via `.todo-cli.json`. |
|
|
321
|
+
| `source/services/TodoCLI-Service-API.js` | Fable service wrapping `http.request()` with JSON parsing and FilteredTo URL construction. |
|
|
322
|
+
| `source/commands/list/TodoCLI-Command-List.js` | `todo list` -- tabular output with `--search`, `--column`, `--direction`, `--limit`, `--status` options. |
|
|
323
|
+
| `source/commands/add/TodoCLI-Command-Add.js` | `todo add <name>` -- create a task with `--due`, `--hours`, `--description`, `--status`. |
|
|
324
|
+
| `source/commands/remove/TodoCLI-Command-Remove.js` | `todo remove <id>` -- delete a task by ID. |
|
|
325
|
+
| `source/commands/complete/TodoCLI-Command-Complete.js` | `todo complete <id>` -- mark a task as complete (fetches first, skips if already done). |
|
|
326
|
+
|
|
327
|
+
## Retold Patterns Demonstrated
|
|
328
|
+
|
|
329
|
+
| Pattern | Where |
|
|
330
|
+
|---------|-------|
|
|
331
|
+
| Fable service provider | All components |
|
|
332
|
+
| Orator HTTP server (Restify) | `server/server.cjs` |
|
|
333
|
+
| Meadow DAL + SQLite | `server/server.cjs` |
|
|
334
|
+
| Meadow Endpoints (auto REST) | `server/server.cjs` |
|
|
335
|
+
| Stricture MicroDDL | `model/Task.mddl` |
|
|
336
|
+
| Provider-based table creation | `server/database-initialization-service.cjs` |
|
|
337
|
+
| CSV seed data via Meadow DAL | `server/database-initialization-service.cjs` |
|
|
338
|
+
| Pict Application lifecycle | `web-client/source/TodoList-Application.cjs` |
|
|
339
|
+
| Pict Views + Templates | `web-client/source/views/` |
|
|
340
|
+
| Pict Providers | `web-client/source/providers/Provider-TaskData.cjs` |
|
|
341
|
+
| Pict Router (hash routing) | `web-client/source/providers/Router-Config.json` |
|
|
342
|
+
| TemplateSet iteration | `web-client/source/views/View-TaskList.cjs` |
|
|
343
|
+
| View CSS injection | `web-client/source/views/` (inline `/*css*/` strings) |
|
|
344
|
+
| Quackage build system | `web-client/` build config |
|
|
345
|
+
| pict-terminalui + blessed | `console-client/console-client.cjs` |
|
|
346
|
+
| ContentAssignment override | `console-client/` (Pict → blessed widget bridge) |
|
|
347
|
+
| pict-service-commandlineutility | `cli-client/source/TodoCLI-CLIProgram.js` |
|
|
348
|
+
| Command-per-folder pattern | `cli-client/source/commands/` |
|
|
349
|
+
| Fable custom service | `cli-client/source/services/TodoCLI-Service-API.js` |
|
|
350
|
+
|
|
351
|
+
## Data Model
|
|
352
|
+
|
|
353
|
+
The Task entity is defined in Stricture MicroDDL (`model/Task.mddl`):
|
|
354
|
+
|
|
355
|
+
```
|
|
356
|
+
!Task
|
|
357
|
+
@IDTask
|
|
358
|
+
%GUIDTask
|
|
359
|
+
$Name 200
|
|
360
|
+
*Description
|
|
361
|
+
&DueDate
|
|
362
|
+
.LengthInHours 10,2
|
|
363
|
+
$Status 32
|
|
364
|
+
&CreateDate
|
|
365
|
+
#CreatingIDUser -> IDUser
|
|
366
|
+
&UpdateDate
|
|
367
|
+
#UpdatingIDUser -> IDUser
|
|
368
|
+
^Deleted
|
|
369
|
+
&DeleteDate
|
|
370
|
+
#DeletingIDUser -> IDUser
|
|
371
|
+
```
|
|
372
|
+
|
|
373
|
+
| Field | Type | Description |
|
|
374
|
+
|-------|------|-------------|
|
|
375
|
+
| IDTask | AutoIdentity | Primary key |
|
|
376
|
+
| GUIDTask | AutoGUID | UUID identifier |
|
|
377
|
+
| Name | String(200) | Task name |
|
|
378
|
+
| Description | Text | Task description |
|
|
379
|
+
| DueDate | DateTime | Due date |
|
|
380
|
+
| LengthInHours | Decimal(10,2) | Estimated hours |
|
|
381
|
+
| Status | String(32) | Pending, In Progress, or Complete |
|
|
382
|
+
|
|
383
|
+
## Seed Data
|
|
384
|
+
|
|
385
|
+
The file `model/data/seeded_todo_events.csv` contains 1,000 realistic task
|
|
386
|
+
events spanning four years, including personal errands, work tasks, birthdays,
|
|
387
|
+
holidays, bills, vet appointments and more.
|
|
388
|
+
|
|
389
|
+
On first run the `DatabaseInitializationService` checks whether the Task table
|
|
390
|
+
is empty. If it is, it reads the CSV and inserts each row through the Meadow
|
|
391
|
+
DAL using `doCreate()`, so every record gets a proper GUID, audit timestamps
|
|
392
|
+
and default values -- exactly as if a user had created them through the API.
|
|
393
|
+
|
|
394
|
+
To re-seed, delete `server/data/todo.sqlite` and restart the server.
|