ask-marcel-office-cli 0.1.0

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.
Files changed (115) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +267 -0
  3. package/dist/cli.js +27084 -0
  4. package/dist/composition/build-deps.d.ts +15 -0
  5. package/dist/composition/cli.d.ts +11 -0
  6. package/dist/composition/env.d.ts +2 -0
  7. package/dist/domain/access-token.d.ts +13 -0
  8. package/dist/domain/env-var.d.ts +10 -0
  9. package/dist/domain/jwt-utils.d.ts +3 -0
  10. package/dist/domain/result.d.ts +19 -0
  11. package/dist/domain/utilities/format-error.d.ts +1 -0
  12. package/dist/index.d.ts +21 -0
  13. package/dist/index.js +24823 -0
  14. package/dist/infra/auth.d.ts +23 -0
  15. package/dist/infra/browser-auth.d.ts +59 -0
  16. package/dist/infra/filesystem-bun.d.ts +2 -0
  17. package/dist/infra/filesystem-node.d.ts +2 -0
  18. package/dist/infra/graph-client.d.ts +20 -0
  19. package/dist/infra/logger.d.ts +5 -0
  20. package/dist/main.d.ts +1 -0
  21. package/dist/presenter/output.d.ts +4 -0
  22. package/dist/use-cases/commands/build-command.d.ts +4 -0
  23. package/dist/use-cases/commands/command-types.d.ts +10 -0
  24. package/dist/use-cases/commands/download-onedrive-file-content.d.ts +9 -0
  25. package/dist/use-cases/commands/get-calendar-event.d.ts +6 -0
  26. package/dist/use-cases/commands/get-calendar-view.d.ts +4 -0
  27. package/dist/use-cases/commands/get-channel-files-folder.d.ts +7 -0
  28. package/dist/use-cases/commands/get-channel-message-hosted-content.d.ts +9 -0
  29. package/dist/use-cases/commands/get-channel-message.d.ts +8 -0
  30. package/dist/use-cases/commands/get-chat-message-hosted-content.d.ts +8 -0
  31. package/dist/use-cases/commands/get-chat-message.d.ts +7 -0
  32. package/dist/use-cases/commands/get-chat.d.ts +6 -0
  33. package/dist/use-cases/commands/get-current-user.d.ts +4 -0
  34. package/dist/use-cases/commands/get-drive-delta.d.ts +7 -0
  35. package/dist/use-cases/commands/get-drive-item.d.ts +7 -0
  36. package/dist/use-cases/commands/get-drive-root-item.d.ts +6 -0
  37. package/dist/use-cases/commands/get-excel-range.d.ts +9 -0
  38. package/dist/use-cases/commands/get-excel-table.d.ts +8 -0
  39. package/dist/use-cases/commands/get-mail-attachment.d.ts +7 -0
  40. package/dist/use-cases/commands/get-mail-message.d.ts +6 -0
  41. package/dist/use-cases/commands/get-mailbox-settings.d.ts +4 -0
  42. package/dist/use-cases/commands/get-my-profile-photo.d.ts +4 -0
  43. package/dist/use-cases/commands/get-onenote-page-content.d.ts +6 -0
  44. package/dist/use-cases/commands/get-outlook-contact.d.ts +6 -0
  45. package/dist/use-cases/commands/get-planner-bucket.d.ts +6 -0
  46. package/dist/use-cases/commands/get-planner-plan.d.ts +6 -0
  47. package/dist/use-cases/commands/get-planner-task-details.d.ts +6 -0
  48. package/dist/use-cases/commands/get-planner-task.d.ts +6 -0
  49. package/dist/use-cases/commands/get-sharepoint-site-by-path.d.ts +7 -0
  50. package/dist/use-cases/commands/get-sharepoint-site-drive-by-id.d.ts +7 -0
  51. package/dist/use-cases/commands/get-sharepoint-site-item.d.ts +7 -0
  52. package/dist/use-cases/commands/get-sharepoint-site-list-item.d.ts +8 -0
  53. package/dist/use-cases/commands/get-sharepoint-site-list.d.ts +7 -0
  54. package/dist/use-cases/commands/get-sharepoint-site.d.ts +6 -0
  55. package/dist/use-cases/commands/get-sharepoint-sites-delta.d.ts +4 -0
  56. package/dist/use-cases/commands/get-specific-calendar-event.d.ts +7 -0
  57. package/dist/use-cases/commands/get-specific-calendar-view.d.ts +6 -0
  58. package/dist/use-cases/commands/get-team-channel.d.ts +7 -0
  59. package/dist/use-cases/commands/get-team.d.ts +6 -0
  60. package/dist/use-cases/commands/get-todo-task.d.ts +7 -0
  61. package/dist/use-cases/commands/index.d.ts +3 -0
  62. package/dist/use-cases/commands/list-all-onenote-sections.d.ts +4 -0
  63. package/dist/use-cases/commands/list-calendar-event-instances.d.ts +7 -0
  64. package/dist/use-cases/commands/list-calendar-events-delta.d.ts +4 -0
  65. package/dist/use-cases/commands/list-calendar-events.d.ts +4 -0
  66. package/dist/use-cases/commands/list-calendar-view-delta.d.ts +4 -0
  67. package/dist/use-cases/commands/list-calendars.d.ts +4 -0
  68. package/dist/use-cases/commands/list-channel-message-hosted-contents.d.ts +8 -0
  69. package/dist/use-cases/commands/list-channel-message-replies.d.ts +8 -0
  70. package/dist/use-cases/commands/list-channel-messages.d.ts +7 -0
  71. package/dist/use-cases/commands/list-channel-tabs.d.ts +7 -0
  72. package/dist/use-cases/commands/list-chat-members.d.ts +6 -0
  73. package/dist/use-cases/commands/list-chat-message-hosted-contents.d.ts +7 -0
  74. package/dist/use-cases/commands/list-chat-message-replies.d.ts +7 -0
  75. package/dist/use-cases/commands/list-chat-messages.d.ts +6 -0
  76. package/dist/use-cases/commands/list-chats.d.ts +4 -0
  77. package/dist/use-cases/commands/list-drive-item-permissions.d.ts +7 -0
  78. package/dist/use-cases/commands/list-drive-item-versions.d.ts +7 -0
  79. package/dist/use-cases/commands/list-drives.d.ts +4 -0
  80. package/dist/use-cases/commands/list-excel-table-rows.d.ts +8 -0
  81. package/dist/use-cases/commands/list-excel-tables.d.ts +7 -0
  82. package/dist/use-cases/commands/list-excel-worksheets.d.ts +7 -0
  83. package/dist/use-cases/commands/list-folder-files.d.ts +7 -0
  84. package/dist/use-cases/commands/list-joined-teams.d.ts +4 -0
  85. package/dist/use-cases/commands/list-mail-attachments.d.ts +6 -0
  86. package/dist/use-cases/commands/list-mail-child-folders.d.ts +6 -0
  87. package/dist/use-cases/commands/list-mail-folder-messages.d.ts +6 -0
  88. package/dist/use-cases/commands/list-mail-folders.d.ts +4 -0
  89. package/dist/use-cases/commands/list-mail-messages.d.ts +4 -0
  90. package/dist/use-cases/commands/list-mail-rules.d.ts +6 -0
  91. package/dist/use-cases/commands/list-onenote-notebook-sections.d.ts +6 -0
  92. package/dist/use-cases/commands/list-onenote-notebooks.d.ts +4 -0
  93. package/dist/use-cases/commands/list-onenote-section-pages.d.ts +6 -0
  94. package/dist/use-cases/commands/list-outlook-contacts.d.ts +4 -0
  95. package/dist/use-cases/commands/list-pinned-chat-messages.d.ts +6 -0
  96. package/dist/use-cases/commands/list-plan-buckets.d.ts +6 -0
  97. package/dist/use-cases/commands/list-plan-tasks.d.ts +6 -0
  98. package/dist/use-cases/commands/list-planner-tasks.d.ts +4 -0
  99. package/dist/use-cases/commands/list-sharepoint-site-drives.d.ts +6 -0
  100. package/dist/use-cases/commands/list-sharepoint-site-items.d.ts +6 -0
  101. package/dist/use-cases/commands/list-sharepoint-site-list-items.d.ts +7 -0
  102. package/dist/use-cases/commands/list-sharepoint-site-lists.d.ts +6 -0
  103. package/dist/use-cases/commands/list-specific-calendar-events.d.ts +6 -0
  104. package/dist/use-cases/commands/list-team-channels.d.ts +6 -0
  105. package/dist/use-cases/commands/list-team-members.d.ts +6 -0
  106. package/dist/use-cases/commands/list-todo-linked-resources.d.ts +7 -0
  107. package/dist/use-cases/commands/list-todo-task-lists.d.ts +4 -0
  108. package/dist/use-cases/commands/list-todo-tasks.d.ts +6 -0
  109. package/dist/use-cases/commands/login.d.ts +6 -0
  110. package/dist/use-cases/commands/logout.d.ts +6 -0
  111. package/dist/use-cases/commands/search-onedrive-files.d.ts +9 -0
  112. package/dist/use-cases/commands/search-sharepoint-sites.d.ts +4 -0
  113. package/dist/use-cases/ports/filesystem.d.ts +15 -0
  114. package/dist/use-cases/ports/logger.d.ts +6 -0
  115. package/package.json +87 -0
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Vincent Delacourt
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,267 @@
1
+ # ask-marcel-office-cli
2
+
3
+ Microsoft Graph CLI — designed for LLM consumption via skills. Explicit commands, compact JSON output, zero interactive prompts beyond auth.
4
+
5
+ ## Commands
6
+
7
+ ### Authentication
8
+
9
+ | Command | Description |
10
+ |---------|-------------|
11
+ | `login` | Authenticate (cached → refresh → browser fallback) |
12
+ | `logout` | Clear cached tokens |
13
+
14
+ ### OneDrive Files
15
+
16
+ | Command | Description | Required params |
17
+ |---------|-------------|-----------------|
18
+ | `list-drives` | List all drives for the authenticated user | _(none)_ |
19
+ | `get-drive-root-item` | Get the root folder of a drive | `--drive-id` |
20
+ | `list-folder-files` | List children of a folder/item | `--drive-id`, `--item-id` |
21
+ | `download-onedrive-file-content` | Get download URL for a file | `--drive-id`, `--item-id` |
22
+ | `get-drive-item` | Get metadata for a file/folder | `--drive-id`, `--item-id` |
23
+ | `list-drive-item-permissions` | List sharing permissions | `--drive-id`, `--item-id` |
24
+ | `list-drive-item-versions` | List file versions | `--drive-id`, `--item-id` |
25
+ | `search-onedrive-files` | Search files by query | `--drive-id`, `--query` |
26
+ | `get-drive-delta` | Get changes since last sync | `--drive-id`, `--item-id` |
27
+
28
+ ### Excel (workbook files)
29
+
30
+ | Command | Description | Required params |
31
+ |---------|-------------|-----------------|
32
+ | `list-excel-worksheets` | List worksheets in a workbook | `--drive-id`, `--item-id` |
33
+ | `list-excel-tables` | List tables in a workbook | `--drive-id`, `--item-id` |
34
+ | `get-excel-table` | Get table details | `--drive-id`, `--item-id`, `--table-id` |
35
+ | `list-excel-table-rows` | List rows in a table | `--drive-id`, `--item-id`, `--table-id` |
36
+ | `get-excel-range` | Get cell values by address | `--drive-id`, `--item-id`, `--worksheet-id`, `--address` |
37
+
38
+ ### SharePoint Sites
39
+
40
+ | Command | Description | Required params |
41
+ |---------|-------------|-----------------|
42
+ | `search-sharepoint-sites` | Search all SharePoint sites | _(none)_ |
43
+ | `get-sharepoint-site` | Get site by ID | `--site-id` |
44
+ | `get-sharepoint-sites-delta` | Get site changes since last sync | _(none)_ |
45
+ | `get-sharepoint-site-by-path` | Get site by URL path | `--site-id`, `--path` |
46
+ | `list-sharepoint-site-drives` | List drives on a site | `--site-id` |
47
+ | `get-sharepoint-site-drive-by-id` | Get site drive by ID | `--site-id`, `--drive-id` |
48
+ | `list-sharepoint-site-items` | List items on a site | `--site-id` |
49
+ | `get-sharepoint-site-item` | Get site item by ID | `--site-id`, `--baseItem-id` |
50
+ | `list-sharepoint-site-lists` | List lists on a site | `--site-id` |
51
+ | `get-sharepoint-site-list` | Get list by ID | `--site-id`, `--list-id` |
52
+ | `list-sharepoint-site-list-items` | List items in a list | `--site-id`, `--list-id` |
53
+ | `get-sharepoint-site-list-item` | Get list item by ID | `--site-id`, `--list-id`, `--listItem-id` |
54
+
55
+ ### Tasks (To Do + Planner)
56
+
57
+ | Command | Description | Required params |
58
+ |---------|-------------|-----------------|
59
+ | `list-todo-task-lists` | List To Do task lists | _(none)_ |
60
+ | `list-todo-tasks` | List tasks in a To Do list | `--todo-task-list-id` |
61
+ | `get-todo-task` | Get a To Do task | `--todo-task-list-id`, `--todo-task-id` |
62
+ | `list-todo-linked-resources` | List resources linked to a To Do task | `--todo-task-list-id`, `--todo-task-id` |
63
+ | `list-planner-tasks` | List Planner tasks for user | _(none)_ |
64
+ | `get-planner-plan` | Get Planner plan by ID | `--planner-plan-id` |
65
+ | `list-plan-tasks` | List tasks in a Planner plan | `--planner-plan-id` |
66
+ | `get-planner-task` | Get Planner task by ID | `--planner-task-id` |
67
+ | `get-planner-task-details` | Get Planner task details | `--planner-task-id` |
68
+ | `list-plan-buckets` | List buckets in a Planner plan | `--planner-plan-id` |
69
+ | `get-planner-bucket` | Get Planner bucket by ID | `--planner-bucket-id` |
70
+
71
+ ### Mail
72
+
73
+ | Command | Description | Required params |
74
+ |---------|-------------|-----------------|
75
+ | `list-mail-messages` | List messages in inbox | _(none)_ |
76
+ | `list-mail-folders` | List mail folders | _(none)_ |
77
+ | `list-mail-child-folders` | List subfolders of a mail folder | `--mail-folder-id` |
78
+ | `list-mail-folder-messages` | List messages in a mail folder | `--mail-folder-id` |
79
+ | `get-mail-message` | Get a message by ID | `--message-id` |
80
+ | `list-mail-attachments` | List attachments on a message | `--message-id` |
81
+ | `get-mail-attachment` | Get an attachment by ID | `--message-id`, `--attachment-id` |
82
+ | `list-mail-rules` | List message rules for a folder | `--mail-folder-id` |
83
+ | `get-mailbox-settings` | Get mailbox settings | _(none)_ |
84
+
85
+ ### Notes (OneNote)
86
+
87
+ | Command | Description | Required params |
88
+ |---------|-------------|-----------------|
89
+ | `list-onenote-notebooks` | List OneNote notebooks | _(none)_ |
90
+ | `list-onenote-notebook-sections` | List sections in a notebook | `--notebook-id` |
91
+ | `list-all-onenote-sections` | List all sections across notebooks | _(none)_ |
92
+ | `list-onenote-section-pages` | List pages in a section | `--onenote-section-id` |
93
+ | `get-onenote-page-content` | Get OneNote page content | `--onenote-page-id` |
94
+
95
+ ### User
96
+
97
+ | Command | Description | Required params |
98
+ |---------|-------------|-----------------|
99
+ | `get-current-user` | Get current user profile | _(none)_ |
100
+ | `get-my-profile-photo` | Get current user profile photo | _(none)_ |
101
+
102
+ ### Calendar
103
+
104
+ | Command | Description | Required params |
105
+ |---------|-------------|-----------------|
106
+ | `list-calendars` | List all calendars | _(none)_ |
107
+ | `list-calendar-events` | List events in default calendar | _(none)_ |
108
+ | `get-calendar-event` | Get event by ID | `--event-id` |
109
+ | `list-specific-calendar-events` | List events in a specific calendar | `--calendar-id` |
110
+ | `get-specific-calendar-event` | Get event in a specific calendar | `--calendar-id`, `--event-id` |
111
+ | `get-calendar-view` | Get calendar view (expanded recurrences) | _(none)_ |
112
+ | `get-specific-calendar-view` | Get calendar view for a specific calendar | `--calendar-id` |
113
+ | `list-calendar-event-instances` | List instances of a recurring event | `--calendar-id`, `--event-id` |
114
+ | `list-calendar-events-delta` | Incremental sync of events | _(none)_ |
115
+ | `list-calendar-view-delta` | Incremental sync within a time window | _(none)_ |
116
+
117
+ ### Contacts
118
+
119
+ | Command | Description | Required params |
120
+ |---------|-------------|-----------------|
121
+ | `list-outlook-contacts` | List Outlook contacts | _(none)_ |
122
+ | `get-outlook-contact` | Get contact by ID | `--contact-id` |
123
+
124
+ ### Chats
125
+
126
+ | Command | Description | Required params |
127
+ |---------|-------------|-----------------|
128
+ | `list-chats` | List Teams chats | _(none)_ |
129
+ | `get-chat` | Get chat by ID | `--chat-id` |
130
+ | `list-chat-members` | List chat members | `--chat-id` |
131
+ | `list-chat-messages` | List chat messages | `--chat-id` |
132
+ | `get-chat-message` | Get chat message by ID | `--chat-id`, `--chat-message-id` |
133
+ | `list-chat-message-hosted-contents` | List message hosted content | `--chat-id`, `--chat-message-id` |
134
+ | `get-chat-message-hosted-content` | Get hosted content bytes | `--chat-id`, `--chat-message-id`, `--chat-message-hosted-content-id` |
135
+ | `list-chat-message-replies` | List message replies | `--chat-id`, `--chat-message-id` |
136
+ | `list-pinned-chat-messages` | List pinned messages | `--chat-id` |
137
+
138
+ ### Teams
139
+
140
+ | Command | Description | Required params |
141
+ |---------|-------------|-----------------|
142
+ | `list-joined-teams` | List joined Teams | _(none)_ |
143
+ | `get-team` | Get team by ID | `--team-id` |
144
+ | `list-team-channels` | List team channels | `--team-id` |
145
+ | `get-team-channel` | Get channel by ID | `--team-id`, `--channel-id` |
146
+ | `list-channel-messages` | List channel messages | `--team-id`, `--channel-id` |
147
+ | `get-channel-message` | Get channel message by ID | `--team-id`, `--channel-id`, `--chat-message-id` |
148
+ | `list-channel-message-hosted-contents` | List message hosted content | `--team-id`, `--channel-id`, `--chat-message-id` |
149
+ | `get-channel-message-hosted-content` | Get hosted content bytes | `--team-id`, `--channel-id`, `--chat-message-id`, `--chat-message-hosted-content-id` |
150
+ | `list-channel-message-replies` | List message replies | `--team-id`, `--channel-id`, `--chat-message-id` |
151
+ | `list-channel-tabs` | List channel tabs | `--team-id`, `--channel-id` |
152
+ | `list-team-members` | List team members | `--team-id` |
153
+ | `get-channel-files-folder` | Get channel files folder | `--team-id`, `--channel-id` |
154
+
155
+ ## Install
156
+
157
+ Requires Node ≥20 **or** Bun ≥1.0 on the user's machine. Works on Windows, macOS, and Linux.
158
+
159
+ ```bash
160
+ npm i -g ask-marcel-office-cli # any platform with Node
161
+ # — or —
162
+ bun add -g ask-marcel-office-cli # any platform with Bun
163
+ ```
164
+
165
+ The first launch prints a one-time notice if a newer version is on npm; update with the same command above plus `@latest`.
166
+
167
+ ## Usage (CLI)
168
+
169
+ ```bash
170
+ # authenticate (cached → refresh → browser fallback)
171
+ ask-marcel login
172
+
173
+ # list drives
174
+ ask-marcel list-drives
175
+
176
+ # search for files
177
+ ask-marcel search-onedrive-files --drive-id abc123 --query "report"
178
+
179
+ # get Excel table data
180
+ ask-marcel list-excel-table-rows --drive-id abc123 --item-id xyz789 --table-id table1
181
+
182
+ # search SharePoint sites
183
+ ask-marcel search-sharepoint-sites
184
+
185
+ # list SharePoint site lists
186
+ ask-marcel list-sharepoint-site-lists --site-id contoso.sharepoint.com,1234-5678
187
+
188
+ # clear tokens
189
+ ask-marcel logout
190
+
191
+ # see all commands
192
+ ask-marcel --help
193
+ ```
194
+
195
+ During development from a clone you can keep using `bun run src/main.ts <command>`.
196
+
197
+ ## Usage (library)
198
+
199
+ The package exports a typed library API for embedding inside your own CLI, agent, or service.
200
+
201
+ ```ts
202
+ import { commands, createGraphClient, buildDeps, type Result } from 'ask-marcel-office-cli';
203
+
204
+ // option 1 — full ladder with built-in OAuth and file cache
205
+ const { graph } = buildDeps();
206
+ const result = await commands['list-drives'].execute(graph, {});
207
+ if (result.ok) console.log(result.value);
208
+
209
+ // option 2 — bring your own AuthManager / token
210
+ const graph = createGraphClient({
211
+ getAccessToken: async () => ({ ok: true, value: process.env.MS_GRAPH_TOKEN as never }),
212
+ logout: async () => ({ ok: true, value: undefined }),
213
+ });
214
+ const me = await commands['get-current-user'].execute(graph, {});
215
+ ```
216
+
217
+ The full export list (registry, factories, `Result`, branded types, ports) is in [src/index.ts](src/index.ts).
218
+
219
+ ## Architecture
220
+
221
+ ```
222
+ src/
223
+ domain/ — Result<T,E>, branded value-object types (AccessToken, EnvVar), JWT utilities, format-error
224
+ infra/ — Auth recovery ladder (cache → refresh → Playwright browser), Graph API HTTP client, Winston logger
225
+ use-cases/ — Commands (schemas + execute functions), ports
226
+ composition/ — CLI wiring (Commander), dependency graph
227
+ presenter/ — Compact JSON output formatting
228
+ ```
229
+
230
+ - **Auth**: Three-rung recovery ladder — file-based cached JWT → OAuth refresh_token exchange → Playwright browser intercepting Teams login
231
+ - **Client ID**: `5e3ce6c0-2b1f-4285-8d4b-75ee78787346` (Teams Web)
232
+ - **Scopes**: `https://graph.microsoft.com/.default openid profile offline_access`
233
+ - **Token cache**: `~/.ask-marcel/token-cache.json` (overridable via `BuildDepsConfig.cachePath`)
234
+ - **Browser profile**: `~/.ask-marcel/browser-profile` (overridable via `ASKMARCEL_BROWSER_PROFILE`)
235
+ - **Output**: Compact JSON via `JSON.stringify` — no indentation, optimised for LLM token efficiency
236
+
237
+ ## Configuration
238
+
239
+ Environment variables read at composition time:
240
+
241
+ | Variable | Used by | Default |
242
+ |---|---|---|
243
+ | `LOG_LEVEL` | Winston logger | `info` |
244
+ | `HOME` / `USERPROFILE` | Default cache and browser-profile paths | _(required)_ |
245
+ | `ASKMARCEL_BROWSER_PROFILE` | Override Playwright user-data-dir | _(none)_ |
246
+
247
+ `HTTP_PROXY` / `HTTPS_PROXY` / `http_proxy` / `https_proxy` are stripped from the process environment immediately before launching Playwright (see `src/infra/browser-auth.ts`).
248
+
249
+ ## Quality gates (atelier four-check loop)
250
+
251
+ ```bash
252
+ bun test # 303 tests
253
+ bun run lint # ESLint (0 warnings, 0 errors)
254
+ bun run typecheck # tsc --noEmit
255
+ bun run coverage # per-tier gates (100% domain + use-cases, 80% infra + composition + presenter)
256
+ bun run mutate:changed # mutation testing on changed domain/use-case files (>90% kill threshold)
257
+ ```
258
+
259
+ ### Pre-commit hook (atelier 8 gates)
260
+
261
+ The repo ships an 8-gate hook at `.githooks/pre-commit` (commit size → package.json → gitleaks → tests → strict lint → typecheck → coverage → mutation). Install once per clone:
262
+
263
+ ```bash
264
+ git config core.hooksPath .githooks
265
+ ```
266
+
267
+ Optional but recommended: install [gitleaks](https://github.com/gitleaks/gitleaks) (`brew install gitleaks`) to enable gate 3. The hook degrades gracefully if it's missing.