@codetreker/daynight 0.21.9 → 0.21.13
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 +359 -27
- package/dist/api/client.d.ts +4 -1
- package/dist/api/client.js +18 -1
- package/dist/api/client.js.map +1 -1
- package/dist/api/parse.d.ts +3 -1
- package/dist/api/parse.js +27 -0
- package/dist/api/parse.js.map +1 -1
- package/dist/api/types.d.ts +18 -3
- package/dist/cli/commands.js +2 -0
- package/dist/cli/commands.js.map +1 -1
- package/dist/commands/skill/skills/using-daynight/references/handoff.md +3 -3
- package/dist/commands/worker/cleanup.d.ts +6 -0
- package/dist/commands/worker/cleanup.js +173 -0
- package/dist/commands/worker/cleanup.js.map +1 -0
- package/dist/commands/worker/config.d.ts +21 -0
- package/dist/commands/worker/config.js +144 -0
- package/dist/commands/worker/config.js.map +1 -0
- package/dist/commands/worker/control.d.ts +55 -0
- package/dist/commands/worker/control.js +151 -0
- package/dist/commands/worker/control.js.map +1 -0
- package/dist/commands/worker/coordinator.d.ts +35 -0
- package/dist/commands/worker/coordinator.js +548 -0
- package/dist/commands/worker/coordinator.js.map +1 -0
- package/dist/commands/worker/definition.d.ts +2 -0
- package/dist/commands/worker/definition.js +50 -0
- package/dist/commands/worker/definition.js.map +1 -0
- package/dist/commands/worker/diagnostics.d.ts +20 -0
- package/dist/commands/worker/diagnostics.js +56 -0
- package/dist/commands/worker/diagnostics.js.map +1 -0
- package/dist/commands/worker/execution.d.ts +41 -0
- package/dist/commands/worker/execution.js +318 -0
- package/dist/commands/worker/execution.js.map +1 -0
- package/dist/commands/worker/herdr/agents.d.ts +186 -0
- package/dist/commands/worker/herdr/agents.js +726 -0
- package/dist/commands/worker/herdr/agents.js.map +1 -0
- package/dist/commands/worker/herdr/arguments.d.ts +8 -0
- package/dist/commands/worker/herdr/arguments.js +58 -0
- package/dist/commands/worker/herdr/arguments.js.map +1 -0
- package/dist/commands/worker/herdr/codex-input.d.ts +2 -0
- package/dist/commands/worker/herdr/codex-input.js +35 -0
- package/dist/commands/worker/herdr/codex-input.js.map +1 -0
- package/dist/commands/worker/herdr/command.d.ts +22 -0
- package/dist/commands/worker/herdr/command.js +115 -0
- package/dist/commands/worker/herdr/command.js.map +1 -0
- package/dist/commands/worker/herdr/instance.d.ts +56 -0
- package/dist/commands/worker/herdr/instance.js +322 -0
- package/dist/commands/worker/herdr/instance.js.map +1 -0
- package/dist/commands/worker/herdr/preflight.d.ts +40 -0
- package/dist/commands/worker/herdr/preflight.js +251 -0
- package/dist/commands/worker/herdr/preflight.js.map +1 -0
- package/dist/commands/worker/herdr/rpc.d.ts +29 -0
- package/dist/commands/worker/herdr/rpc.js +186 -0
- package/dist/commands/worker/herdr/rpc.js.map +1 -0
- package/dist/commands/worker/herdr.d.ts +95 -0
- package/dist/commands/worker/herdr.js +35 -0
- package/dist/commands/worker/herdr.js.map +1 -0
- package/dist/commands/worker/index.d.ts +18 -0
- package/dist/commands/worker/index.js +58 -0
- package/dist/commands/worker/index.js.map +1 -0
- package/dist/commands/worker/instance-lock.d.ts +5 -0
- package/dist/commands/worker/instance-lock.js +11 -1
- package/dist/commands/worker/instance-lock.js.map +1 -1
- package/dist/commands/worker/prompts.d.ts +4 -0
- package/dist/commands/worker/prompts.js +64 -0
- package/dist/commands/worker/prompts.js.map +1 -0
- package/dist/commands/worker/remote.d.ts +23 -0
- package/dist/commands/worker/remote.js +146 -0
- package/dist/commands/worker/remote.js.map +1 -0
- package/dist/commands/worker/runtime.d.ts +16 -0
- package/dist/commands/worker/runtime.js +384 -0
- package/dist/commands/worker/runtime.js.map +1 -0
- package/dist/commands/worker/store.d.ts +73 -5
- package/dist/commands/worker/store.js +475 -36
- package/dist/commands/worker/store.js.map +1 -1
- package/dist/commands/worker/types.d.ts +37 -1
- package/dist/commands/worker/worktrees.d.ts +1 -0
- package/dist/commands/worker/worktrees.js +9 -0
- package/dist/commands/worker/worktrees.js.map +1 -1
- package/dist/config/document.d.ts +1 -1
- package/dist/config/document.js +1 -0
- package/dist/config/document.js.map +1 -1
- package/dist/platform/instance-lock.d.ts +4 -0
- package/dist/platform/instance-lock.js +9 -1
- package/dist/platform/instance-lock.js.map +1 -1
- package/package.json +2 -2
package/README.md
CHANGED
|
@@ -2,8 +2,9 @@
|
|
|
2
2
|
|
|
3
3
|
The `@codetreker/daynight` package provides the `daynight` command and its `dn`
|
|
4
4
|
alias. Use it to manage server-backed projects, tasks and attachments, install
|
|
5
|
-
the `using-daynight` skill for coding agents,
|
|
6
|
-
through Copilot CLI. Both command names
|
|
5
|
+
the `using-daynight` skill for coding agents, run foreground task workers through
|
|
6
|
+
Herdr, and run a local GitHub PR reviewer through Copilot CLI. Both command names
|
|
7
|
+
share configuration and behavior.
|
|
7
8
|
|
|
8
9
|
See the [project overview](../../README.md) for the browser workspace and service,
|
|
9
10
|
and the [development guide](../../docs/development.md) for source builds,
|
|
@@ -20,6 +21,8 @@ GitHub CLI and Copilot CLI on `PATH`.
|
|
|
20
21
|
- [Task management](#task-management)
|
|
21
22
|
- [Task deletion](#task-deletion)
|
|
22
23
|
- [Task attachments](#task-attachments)
|
|
24
|
+
- [Worker configuration and startup](#worker-configuration-and-startup)
|
|
25
|
+
- [Worker manual management](#worker-manual-management)
|
|
23
26
|
- [Review configuration and startup](#review-configuration-and-startup)
|
|
24
27
|
- [Review status listing](#review-status-listing)
|
|
25
28
|
- [Durable review state](#durable-review-state)
|
|
@@ -78,11 +81,11 @@ its agents, scope, path and package version. A skill failure exits nonzero and
|
|
|
78
81
|
reports the package outcome separately; a successfully installed npm package is
|
|
79
82
|
retained, and rerunning `update` retries the skill refresh. All phases must
|
|
80
83
|
succeed before the command reports success. It requires no review configuration and does
|
|
81
|
-
not open SQLite, modify sessions or restart a running reviewer. The next CLI
|
|
82
|
-
invocation uses the installed version. Restart any running reviewer to use it;
|
|
83
|
-
on Windows, a reviewer holding a native addon open can prevent npm from replacing
|
|
84
|
+
not open SQLite, modify sessions or restart a running reviewer or worker. The next CLI
|
|
85
|
+
invocation uses the installed version. Restart any running reviewer or worker to use it;
|
|
86
|
+
on Windows, a reviewer or worker holding a native addon open can prevent npm from replacing
|
|
84
87
|
that file and cause the update to fail. The
|
|
85
|
-
[self-update decision](../../.agents/notes/
|
|
88
|
+
[self-update decision](../../.agents/notes/archived/feature/2026-10-20-cli-self-update.md)
|
|
86
89
|
records installation ownership and verification requirements.
|
|
87
90
|
|
|
88
91
|
## Client commands
|
|
@@ -94,6 +97,12 @@ daynight --version # Also -v
|
|
|
94
97
|
daynight update
|
|
95
98
|
daynight login [--no-browser] # Authorize CLI access through the browser
|
|
96
99
|
daynight logout # Revoke and remove the current CLI credential
|
|
100
|
+
daynight worker # Show worker help
|
|
101
|
+
daynight worker run # Run until interrupted
|
|
102
|
+
daynight worker retry <task-id> --claim-id <claim-id> [--project <project-id>]
|
|
103
|
+
daynight worker release <task-id> --claim-id <claim-id> --if-version <version> [--project <project-id>]
|
|
104
|
+
daynight worker resume <task-id> --claim-id <previous-claim-id> --if-version <version> [--project <project-id>]
|
|
105
|
+
daynight worker transfer <task-id> --claim-id <claim-id> --if-version <version> [target options] [--project <project-id>]
|
|
97
106
|
daynight review # Show review help
|
|
98
107
|
daynight review run
|
|
99
108
|
daynight review list # Also review ls
|
|
@@ -132,7 +141,7 @@ Unknown commands and invalid arguments exit with status 2; operation failures
|
|
|
132
141
|
exit with status 1 and retain their cause. The old `--daemon-review` and root
|
|
133
142
|
`add-repo` forms are invalid. The
|
|
134
143
|
[client design](../../docs/design/daynight.md) owns command composition and lazy loading;
|
|
135
|
-
the [composition decision](../../.agents/notes/
|
|
144
|
+
the [composition decision](../../.agents/notes/archived/architecture/2026-10-20-client-command-composition.md)
|
|
136
145
|
records module ownership and the preserved data layout.
|
|
137
146
|
|
|
138
147
|
## Agent skill installation
|
|
@@ -144,7 +153,8 @@ prompt explicitly names the `worker-managed` environment, the `using-daynight`
|
|
|
144
153
|
skill and that mode, together with their assignment. `SKILL.md` routes to the
|
|
145
154
|
selected instructions; ordinary execution does not load managed task rules.
|
|
146
155
|
Shared task inputs, delivery and acceptance rules retain one owner in the bundle.
|
|
147
|
-
The worker
|
|
156
|
+
The [foreground worker](#worker-configuration-and-startup) constructs that
|
|
157
|
+
explicit assignment and loads the installed managed entry before launch.
|
|
148
158
|
|
|
149
159
|
Install the skill through an interactive terminal:
|
|
150
160
|
|
|
@@ -293,9 +303,9 @@ update, run the applicable `source` command again to refresh an existing shell.
|
|
|
293
303
|
A saved generated script must be regenerated after updating. The
|
|
294
304
|
[completion design](../../docs/design/daynight-completion.md) explains the shared grammar
|
|
295
305
|
and shell integration. The
|
|
296
|
-
[completion decision](../../.agents/notes/
|
|
306
|
+
[completion decision](../../.agents/notes/archived/feature/2026-10-20-shell-completion.md)
|
|
297
307
|
records compatibility and execution trade-offs; the
|
|
298
|
-
[setup decision](../../.agents/notes/
|
|
308
|
+
[setup decision](../../.agents/notes/archived/feature/2026-10-21-completion-setup.md)
|
|
299
309
|
records startup-file ownership and installation limits.
|
|
300
310
|
|
|
301
311
|
## Configuration setup
|
|
@@ -382,8 +392,8 @@ business execution. Human input consumes no business timeout. Review guidance
|
|
|
382
392
|
saves configuration without network, login or authentication checks; cloning and
|
|
383
393
|
review state initialization belong to the business operation.
|
|
384
394
|
|
|
385
|
-
The [configuration decision](../../.agents/notes/
|
|
386
|
-
|
|
395
|
+
The [configuration decision](../../.agents/notes/archived/feature/2026-10-21-guided-configuration-setup.md)
|
|
396
|
+
records the review-guidance and persistence choices; the
|
|
387
397
|
[device-login decision](../../.agents/notes/implemented/architecture/2026-10-25-cli-device-login.md)
|
|
388
398
|
owns the default service, explicit login/logout and credential lifecycle. The
|
|
389
399
|
[top-level setup removal decision](../../.agents/notes/implemented/simplification/2026-10-25-remove-top-level-setup.md)
|
|
@@ -744,9 +754,329 @@ known issue and the trusted same-origin preview model. The
|
|
|
744
754
|
[authentication architecture](../../docs/design/daynight-auth.md) defines the required
|
|
745
755
|
authentication and project-membership checks for attachment requests. Trusted
|
|
746
756
|
executable HTML retains the application origin. The
|
|
747
|
-
[CLI delivery decision](../../.agents/notes/
|
|
757
|
+
[CLI delivery decision](../../.agents/notes/archived/feature/2026-10-21-task-attachment-cli.md)
|
|
748
758
|
records binary transport and output ownership.
|
|
749
759
|
|
|
760
|
+
## Worker configuration and startup
|
|
761
|
+
|
|
762
|
+
`daynight worker run` is a foreground process that claims eligible ready tasks
|
|
763
|
+
across configured repositories and runs Copilot or Codex in a dedicated Herdr
|
|
764
|
+
instance. The agent owns task delivery, acceptance, evidence and final
|
|
765
|
+
claim-bound completion. The worker owns concurrency, resources, recovery and
|
|
766
|
+
cleanup based on its current claim inventory.
|
|
767
|
+
|
|
768
|
+
Install Git, Herdr 0.9.5 or newer with protocol 22 capabilities, and the selected
|
|
769
|
+
native agent on PATH. Native/provider authentication and the current official
|
|
770
|
+
Herdr SessionStart integration must be configured explicitly. Codex needs the
|
|
771
|
+
hooks feature and `--no-daemon`; Unix hook scripts need bash and python3, while
|
|
772
|
+
Windows hooks need PowerShell. The worker reports missing capabilities or
|
|
773
|
+
integration/history instead of installing or changing global native settings.
|
|
774
|
+
Git transport and tools used by the task, such as authenticated GitHub CLI for
|
|
775
|
+
PR delivery, must also be ready.
|
|
776
|
+
|
|
777
|
+
Run `daynight login` for Daynight authentication. Add the following mapping to
|
|
778
|
+
the shared `~/.daynight/config.yml`, preserving existing connection and review
|
|
779
|
+
settings:
|
|
780
|
+
|
|
781
|
+
```yaml
|
|
782
|
+
worker:
|
|
783
|
+
maxConcurrent: 1
|
|
784
|
+
pollIntervalMs: 5000
|
|
785
|
+
recoveryLimit: 3
|
|
786
|
+
agent: copilot
|
|
787
|
+
model: null
|
|
788
|
+
args: []
|
|
789
|
+
repositories:
|
|
790
|
+
- remote: https://github.com/OWNER/REPO.git
|
|
791
|
+
path: ../code/repo
|
|
792
|
+
- remote: https://github.com/OWNER/OTHER.git
|
|
793
|
+
path: ../code/other
|
|
794
|
+
agent: codex
|
|
795
|
+
model: null
|
|
796
|
+
args: []
|
|
797
|
+
```
|
|
798
|
+
|
|
799
|
+
These are the defaults for all optional worker fields; `repositories` is
|
|
800
|
+
required. Each entry requires `remote` and `path`, with optional `projectId`,
|
|
801
|
+
`agent`, `model` and `args`. The service project must already exist and match the
|
|
802
|
+
repository. Add `projectId` when more than one project matches. Missing local
|
|
803
|
+
repositories are cloned; existing roots and origins are verified without
|
|
804
|
+
resetting their files or branches. Use the native authentication configuration
|
|
805
|
+
for credentials, keeping credentials out of repository URLs and argument lists.
|
|
806
|
+
|
|
807
|
+
Paths are absolute or relative to the configuration file's directory, never
|
|
808
|
+
the launch directory. Tilde expansion and drive-relative Windows paths are
|
|
809
|
+
rejected. Repository identities, project IDs and paths cannot duplicate or
|
|
810
|
+
overlap, including the fixed Daynight state directory. Unknown worker fields,
|
|
811
|
+
wrong types, invalid arguments and unsupported path shapes fail visibly.
|
|
812
|
+
`maxConcurrent` is a positive integer, `recoveryLimit` is nonnegative and
|
|
813
|
+
`pollIntervalMs` is a positive safe integer within the timer range.
|
|
814
|
+
|
|
815
|
+
Repository agent settings override fields independently when the type stays
|
|
816
|
+
the same; explicit null model or an empty args list clears that field. Switching
|
|
817
|
+
agent type clears inherited model and arguments unless the repository explicitly
|
|
818
|
+
sets them. Args replace the list rather than append. The recovery limit is
|
|
819
|
+
worker-wide. Configuration loads at startup, without hot reload; existing claims
|
|
820
|
+
keep their original frozen configuration after a restart, while later claims
|
|
821
|
+
use the newly loaded settings.
|
|
822
|
+
|
|
823
|
+
New tasks have automatic execution disabled. Enable it explicitly with the
|
|
824
|
+
normal task update workflow after reading the current task/version. The worker
|
|
825
|
+
selects only ready, permitted tasks compatible with its actual platform; WSL
|
|
826
|
+
counts as Linux. It never enables that permission itself. Released tasks wait
|
|
827
|
+
for explicit management and do not immediately re-enter ordinary automatic
|
|
828
|
+
acquisition. Run the worker with:
|
|
829
|
+
|
|
830
|
+
```bash
|
|
831
|
+
daynight worker run
|
|
832
|
+
```
|
|
833
|
+
|
|
834
|
+
The command generates and atomically saves a stable root `workerId` on first
|
|
835
|
+
use. One foreground instance owns fixed `~/.daynight/worker/` state: its SQLite,
|
|
836
|
+
instance lock, logs, temporary resources and private Herdr data. There is no
|
|
837
|
+
state-path override. Each task uses `daynight/<task-id>` and
|
|
838
|
+
`<repository>/.worktrees/daynight/<task-id>`. The same valid claim retains dirty
|
|
839
|
+
work, native history and configuration; a new claim has a fresh execution
|
|
840
|
+
identity and conversation.
|
|
841
|
+
|
|
842
|
+
The worker verifies the startup credential through the existing current-user
|
|
843
|
+
API and pins successful response identity, including empty pages. Each local
|
|
844
|
+
claim retains its original Daynight user ID. If another account is logged in on
|
|
845
|
+
the same OS account, the stable workerId stays the same, but that account's empty
|
|
846
|
+
inventory cannot terminate or resume the previous account's work. Scope-paused
|
|
847
|
+
records need the original account/identity inspected; do not remove local state
|
|
848
|
+
or regenerate workerId to make the mismatch disappear. The running process
|
|
849
|
+
keeps its startup credential; restart after an intended account change.
|
|
850
|
+
|
|
851
|
+
Changing serverUrl also separates local responsibility from remote work. The
|
|
852
|
+
worker queries and acquires only on its current service. Previously committed
|
|
853
|
+
cleanup deadlines and normal shutdown cover that worker's local records across
|
|
854
|
+
all original services, without calling an old API or asking the new service
|
|
855
|
+
about old records. A newly granted current-service claim freezes its new
|
|
856
|
+
configuration and waits pending behind any active predecessor with the same task UUID for that
|
|
857
|
+
worker, including another origin. Read-only Git ownership attributes
|
|
858
|
+
an occupied canonical path; it does not adopt the old conversation or config.
|
|
859
|
+
|
|
860
|
+
The foreground stderr output and JSONL logs identify project/task/claim, platform,
|
|
861
|
+
waiting, pause and cleanup errors. The log path is printed at startup. An
|
|
862
|
+
unconfirmed claim request, native launch or input is retained for observation;
|
|
863
|
+
it is not replayed. A pause still reserves capacity. Recovering missing original
|
|
864
|
+
configuration, history or stop evidence requires inspection, without creating a
|
|
865
|
+
replacement conversation to conceal the loss.
|
|
866
|
+
|
|
867
|
+
For human input, copy the safe `attach` descriptor printed after the running
|
|
868
|
+
worker has completed inventory and private managed-instance readiness.
|
|
869
|
+
Invoke its `executable` with its `arguments` (`herdr --session w` for the default
|
|
870
|
+
executable), apply exactly its `environment` overrides and remove the names in
|
|
871
|
+
`unsetEnvironment` **only for that attach client process**. The descriptor's
|
|
872
|
+
private XDG values select the worker's exact Herdr instance; the existing task
|
|
873
|
+
pane keeps its original native XDG and private HISTFILE. The descriptor contains
|
|
874
|
+
routing and native-home paths, not a dump of authentication values. Continue in
|
|
875
|
+
the original task pane so the worker can observe the same execution.
|
|
876
|
+
|
|
877
|
+
Native startup can be waiting at a folder-trust or authorization screen even
|
|
878
|
+
when Herdr reports idle/interactiveReady. The worker checks the current Codex
|
|
879
|
+
input surface before automatic text and Enter, reports a blocking reason and
|
|
880
|
+
keeps the first prompt unsent. It does not choose native trust or change global
|
|
881
|
+
trust configuration. Configure that prerequisite normally in the native tool or
|
|
882
|
+
use the original attached task pane to make the decision explicitly, then leave
|
|
883
|
+
the business composer available for input. This check does not inspect arbitrary
|
|
884
|
+
human draft meaning or prove that a model consumed previously submitted text.
|
|
885
|
+
|
|
886
|
+
The checked Codex startup/restart layout is the standard/default business
|
|
887
|
+
composer together with a loaded model/reasoning and current-directory footer
|
|
888
|
+
(`model-with-reasoning · current-dir`). Ask text or a version header alone is
|
|
889
|
+
insufficient because provisional startup can show them too. A custom footer,
|
|
890
|
+
cropped footer or otherwise unrecognized visible layout remains unknown; the
|
|
891
|
+
original Operation bounds observation and ends not-submitted if that supported
|
|
892
|
+
surface never appears. In the original session, finish any blocking decision
|
|
893
|
+
and restore the supported standard native layout before requesting public retry.
|
|
894
|
+
The worker does not change the layout, infer arbitrary draft meaning or turn
|
|
895
|
+
this screen check into a native consumption receipt.
|
|
896
|
+
|
|
897
|
+
For started executions, a successful complete own-claim inventory from the
|
|
898
|
+
original account makes the original claim's absence cause
|
|
899
|
+
the same terminal cleanup for done, release and transfer: request attributable
|
|
900
|
+
outside-worktree cleanup for at most the original ten-minute deadline, confirm
|
|
901
|
+
the original agent stopped, close its workspace, delete its worktree and retain
|
|
902
|
+
local history. Failures keep responsibility and resume cleanup after restart.
|
|
903
|
+
A failed, incomplete or differently scoped inventory cannot authorize a new
|
|
904
|
+
terminal-cleanup decision. Already persisted cleanup/control intents continue in
|
|
905
|
+
the same foreground process through a lightweight discovery loop and one
|
|
906
|
+
transient asynchronous job per full claim, before current-user/project network
|
|
907
|
+
requests and even during server read failures. Only already authorized intents
|
|
908
|
+
with known original account scope advance; unknown-scope terminal/control
|
|
909
|
+
intents remain preserved. Each job waits at most one second or its nearer
|
|
910
|
+
original deadline, independently of pollIntervalMs. One task's held RPC does not
|
|
911
|
+
postpone another task's next cleanup advance; per-task serialization still
|
|
912
|
+
prevents overlapping operations on the same execution. There is no persisted job
|
|
913
|
+
queue.
|
|
914
|
+
|
|
915
|
+
Ctrl+C stops acquisition and ordinary input, cancels and joins the ordinary
|
|
916
|
+
cleanup discovery loop and all per-claim jobs, then runs original-task shutdown
|
|
917
|
+
with a separate bounded cancellation scope and a shared exit deadline.
|
|
918
|
+
Unfinished claims, worktrees and native history remain; the private instance
|
|
919
|
+
stops only after original agents are confirmed stopped. Stop uncertainty is
|
|
920
|
+
reported and retains the instance/resources for inspection. Restart the command
|
|
921
|
+
to reconcile with the same worker identity and original state. After consuming
|
|
922
|
+
interrupted shutdown, the worker refreshes Herdr resources before ordinary
|
|
923
|
+
execution. If a native launch may have occurred but its exact original session
|
|
924
|
+
ID is missing, shutdown preserves its old binding, launch and PID evidence and
|
|
925
|
+
pauses; it does not turn that execution into a first launch. Proven
|
|
926
|
+
never-started work and executions with a known original native ID retain their
|
|
927
|
+
normal recovery path.
|
|
928
|
+
|
|
929
|
+
A causal worker cancellation propagates into shutdown without adding a fault
|
|
930
|
+
pause. Existing real pauses, recovery budget and unknown-action records keep
|
|
931
|
+
their meaning; an unrelated error is not normal cancellation merely because the
|
|
932
|
+
signal is already aborted. Read-only interruption followed by successful
|
|
933
|
+
shutdown can resume the original session through the normal recovery path.
|
|
934
|
+
|
|
935
|
+
Pending successors whose resources, workspace and native launch are proven
|
|
936
|
+
never started stay pending on normal exit. A successful complete inventory from
|
|
937
|
+
the same original account can complete an absent unstarted claim directly,
|
|
938
|
+
without activating it or touching an older claim's fixed Git path. Other tasks'
|
|
939
|
+
shutdown initialization is isolated so one bad record does not prevent known
|
|
940
|
+
agents stopping. Untracked resources or unknown scope keep the private instance
|
|
941
|
+
when its stop cannot be confirmed.
|
|
942
|
+
|
|
943
|
+
Linux, Windows and macOS complete Goal acceptance is separate from the installed
|
|
944
|
+
runtime and its component checks. The
|
|
945
|
+
[worker requirements](../../docs/spec/daynight-worker.md) and
|
|
946
|
+
[worker design](../../docs/design/daynight-worker.md) own the behavior and
|
|
947
|
+
mechanisms, including native capability limits.
|
|
948
|
+
|
|
949
|
+
## Worker manual management
|
|
950
|
+
|
|
951
|
+
Manual commands select one task and its exact original claim. They use the same
|
|
952
|
+
fixed SQLite and singleton lock as `worker run`. With a foreground worker, that
|
|
953
|
+
process remains the sole agent controller and consumes the persisted decision;
|
|
954
|
+
without one, the command acquires the same lock and advances the same coordinator
|
|
955
|
+
for that execution. There is no separate control service. Current configuration
|
|
956
|
+
and Daynight authentication are required, and the original service origin must
|
|
957
|
+
match. Release, transfer and retry require the unfinished original local record;
|
|
958
|
+
resume can use an explicit project with its configured repository.
|
|
959
|
+
|
|
960
|
+
Read the current task before deciding a versioned operation:
|
|
961
|
+
|
|
962
|
+
```bash
|
|
963
|
+
daynight task show <task-id> --json
|
|
964
|
+
daynight worker release <task-id> --claim-id <source-claim-id> --if-version <version>
|
|
965
|
+
```
|
|
966
|
+
|
|
967
|
+
Release and transfer first verify project access and source owner/admin
|
|
968
|
+
permission, then persist the concrete source decision before cleanup. The
|
|
969
|
+
controller requests the original agent's attributable temporary-resource cleanup,
|
|
970
|
+
waits for its original deadline of at most 10 minutes, confirms that agent stopped,
|
|
971
|
+
closes its task workspace and deletes its worktree. Only then can it submit the
|
|
972
|
+
remote write at the exact supplied version. Other tasks keep their shared Herdr
|
|
973
|
+
instance. Failed stopping or deletion retains the source responsibility and a
|
|
974
|
+
visible error. Cleanup keeps its original deadline after restart; each HTTP
|
|
975
|
+
request has an independent bounded scope, without a five-minute total command
|
|
976
|
+
limit.
|
|
977
|
+
|
|
978
|
+
Release returns the task to `todo` and clears its execution interval. The daemon
|
|
979
|
+
skips released tasks until explicitly resumed. Resume starts a fresh execution
|
|
980
|
+
on this worker:
|
|
981
|
+
|
|
982
|
+
```bash
|
|
983
|
+
daynight worker resume <task-id> --claim-id <released-claim-id> --if-version <version> \
|
|
984
|
+
--project <project-id>
|
|
985
|
+
```
|
|
986
|
+
|
|
987
|
+
The previous claim must still be released and the task ready. The original owner
|
|
988
|
+
or a current project admin may resume it, retaining the explicit manual exception
|
|
989
|
+
to automatic permission and platform filters. The new claim and worktree IDs are
|
|
990
|
+
generated and persisted before submission. Its actual grant commits local
|
|
991
|
+
`pending` with this repository's current effective agent/model/args; `worker run`
|
|
992
|
+
then performs ordinary capacity checks and prepares a fresh native conversation.
|
|
993
|
+
The deleted source worktree and native history are not required. Run
|
|
994
|
+
`daynight worker run` if the foreground worker is stopped.
|
|
995
|
+
|
|
996
|
+
Transfer explicitly identifies the target's current user, stable worker and
|
|
997
|
+
machine descriptor, actual platform and selected agent:
|
|
998
|
+
|
|
999
|
+
```bash
|
|
1000
|
+
daynight worker transfer <task-id> --claim-id <source-claim-id> --if-version <version> \
|
|
1001
|
+
--target-user-id <user-id> --target-worker-id <worker-id> \
|
|
1002
|
+
--target-machine-id <machine-id> --target-machine-name "target-machine" \
|
|
1003
|
+
--target-platform linux --target-agent codex
|
|
1004
|
+
```
|
|
1005
|
+
|
|
1006
|
+
Use the intended receiver's actual descriptor and the explicitly selected new
|
|
1007
|
+
agent type. A trace-free new transfer grant honors that agent even when the
|
|
1008
|
+
receiver's current repository defaults select the other type. It freezes
|
|
1009
|
+
`model: null` and `args: []` for that type, with the current recovery limit; a
|
|
1010
|
+
matching type uses the current effective model/args. Existing pending snapshots
|
|
1011
|
+
are retained. The source operator's owner/admin permission is checked separately
|
|
1012
|
+
from the target's
|
|
1013
|
+
current membership. Transfer still requires automatic execution permission,
|
|
1014
|
+
platform compatibility and completed dependencies. It preserves `in_progress`
|
|
1015
|
+
and the task's execution interval, installing a fresh target claim/worktree ID
|
|
1016
|
+
with empty runtime associations. The receiver discovers its actual grant through
|
|
1017
|
+
normal claim inventory and starts a new execution; an old task path still in use
|
|
1018
|
+
blocks preparation. No source files, SQLite snapshots or native history are
|
|
1019
|
+
transported. Target and source agents may differ. Public commands provide no
|
|
1020
|
+
claim/worktree-ID override or continuity confirmation option; the service and
|
|
1021
|
+
typed client reject deprecated `continuityConfirmed` input.
|
|
1022
|
+
|
|
1023
|
+
For a paused execution that still belongs to the original owner, authorize one
|
|
1024
|
+
extra recovery attempt:
|
|
1025
|
+
|
|
1026
|
+
```bash
|
|
1027
|
+
daynight worker retry <task-id> --claim-id <claim-id>
|
|
1028
|
+
```
|
|
1029
|
+
|
|
1030
|
+
Retry preserves the original claim, worktree/native identity and frozen
|
|
1031
|
+
settings, retaining the cumulative recovery count rather than resetting it.
|
|
1032
|
+
Concurrent or repeated requests do not accumulate extra authorization or launch
|
|
1033
|
+
a second agent. The controller consumes the single permit for that original
|
|
1034
|
+
execution; a further failure remains visible. Retry cannot replace terminal
|
|
1035
|
+
cleanup or recreate an execution that has ended.
|
|
1036
|
+
|
|
1037
|
+
A native launch acknowledged before a blocking startup screen has a specific
|
|
1038
|
+
continuation path when its first prompt is durably known unsent. Keep the
|
|
1039
|
+
original worker/native session running and use another terminal to attach to
|
|
1040
|
+
that original pane. Inspect the reported folder-trust/authorization requirement
|
|
1041
|
+
and make the native decision yourself. Once the business composer is available,
|
|
1042
|
+
run:
|
|
1043
|
+
|
|
1044
|
+
```bash
|
|
1045
|
+
daynight worker retry <task-id> --claim-id <original-claim-id> --project <project-id>
|
|
1046
|
+
```
|
|
1047
|
+
|
|
1048
|
+
The controller first checks the original worktree, full binding, frozen argv,
|
|
1049
|
+
workspace/launch evidence, same shell and every saved native key PID. Ordinary
|
|
1050
|
+
child-process changes do not replace the original proof. After that read-only
|
|
1051
|
+
identity check, it consumes one authorized recovery attempt (the cumulative
|
|
1052
|
+
count increases by one, without reset) and can deliver the first prompt once in
|
|
1053
|
+
the original native process without another agent.start or conversation. Missing
|
|
1054
|
+
an official native ID before the first turn does not by itself block this
|
|
1055
|
+
proven-unsent continuation. This is not permission to resend an earlier
|
|
1056
|
+
submitted/unknown prompt, infer loss from an empty-looking composer or restart
|
|
1057
|
+
an unproven missing-ID conversation. Legacy records with unknown native-process
|
|
1058
|
+
role remain fenced; migration does not construct identity from foreground PID
|
|
1059
|
+
order. Automated cleanup text and /exit use the same screen boundary; a blocking
|
|
1060
|
+
screen is not accepted with Enter merely to finish shutdown.
|
|
1061
|
+
|
|
1062
|
+
Management diagnostics identify the original claim and report persisted waiting,
|
|
1063
|
+
completion, rejection or unknown results. Interrupting the command retains its
|
|
1064
|
+
intent so the foreground controller or a later management invocation can
|
|
1065
|
+
continue. An unknown release/transfer write is reconciled by reading the actual
|
|
1066
|
+
task and saved target claim; it is never resent or assigned replacement IDs,
|
|
1067
|
+
even when a read still shows the old value. Reinvoking that same decision can
|
|
1068
|
+
reconcile its result by targeted reads, including beside a running foreground
|
|
1069
|
+
worker, without taking over resource control or resubmitting. An already-cleaned
|
|
1070
|
+
source is not restarted. Only a definitely rejected submission can be replaced by a new explicit
|
|
1071
|
+
decision, with the supplied `--if-version` matching a fresh task observation. The
|
|
1072
|
+
numeric version may remain the same when the refusal did not change the task,
|
|
1073
|
+
including a definite pre-dispatch failure or permission refusal. An unknown
|
|
1074
|
+
submission cannot be reset or replayed; `--if-version` is never silently replaced.
|
|
1075
|
+
Unknown resume requests likewise retain their original claim/worktree/config
|
|
1076
|
+
until the actual grant can be confirmed. These targeted reads reconcile manual
|
|
1077
|
+
writes; automatic cleanup still relies only on a complete successful inventory
|
|
1078
|
+
for the original authenticated user and worker.
|
|
1079
|
+
|
|
750
1080
|
## Review configuration and startup
|
|
751
1081
|
|
|
752
1082
|
Register a repository explicitly, or let the first review operation guide registration:
|
|
@@ -843,7 +1173,7 @@ review preparation and execution. Startup acquires an exclusive instance lock,
|
|
|
843
1173
|
opens SQLite and prepares the configured clones. Each repository is polled
|
|
844
1174
|
independently; access failures retain its last complete observation and remain
|
|
845
1175
|
visible in diagnostics. The
|
|
846
|
-
[repository registration decision](../../.agents/notes/
|
|
1176
|
+
[repository registration decision](../../.agents/notes/archived/feature/2026-10-18-add-repo-configuration.md)
|
|
847
1177
|
records the fixed-path and configuration-only choices.
|
|
848
1178
|
|
|
849
1179
|
## Review status listing
|
|
@@ -890,7 +1220,7 @@ database, migrate a schema, recover interrupted work or update application state
|
|
|
890
1220
|
SQLite may create or update its WAL coordination sidecar files while reading an
|
|
891
1221
|
existing database. Missing or invalid configuration, unreadable or corrupt state,
|
|
892
1222
|
and unsupported schema versions fail visibly. The
|
|
893
|
-
[listing decision](../../.agents/notes/
|
|
1223
|
+
[listing decision](../../.agents/notes/archived/feature/2026-10-18-review-status-listing.md)
|
|
894
1224
|
records status attribution and snapshot limits.
|
|
895
1225
|
|
|
896
1226
|
## Durable review state
|
|
@@ -925,7 +1255,7 @@ Database state does not replace physical Git/worktree or session-history
|
|
|
925
1255
|
verification.
|
|
926
1256
|
|
|
927
1257
|
See the [review architecture](../../docs/design/daynight-review.md) for transitions and the
|
|
928
|
-
[state decision](../../.agents/notes/
|
|
1258
|
+
[state decision](../../.agents/notes/archived/architecture/2026-10-17-durable-review-state.md)
|
|
929
1259
|
for persistence choices. The coordinator opens this state before scheduling work
|
|
930
1260
|
and advances only the revision captured by each completed attempt.
|
|
931
1261
|
|
|
@@ -941,7 +1271,7 @@ the previous repository observation. A completed pass commits its observations
|
|
|
941
1271
|
and success time atomically. Rate-limit failures expose the server's retry
|
|
942
1272
|
deadline and block later same-host calls in that client; the coordinator schedules
|
|
943
1273
|
the next pass after the applicable deadline.
|
|
944
|
-
The [observation decision](../../.agents/notes/
|
|
1274
|
+
The [observation decision](../../.agents/notes/archived/architecture/2026-10-17-github-observation.md)
|
|
945
1275
|
records pagination and failure handling.
|
|
946
1276
|
|
|
947
1277
|
CI admission uses a read-only GraphQL query for the current PR head and
|
|
@@ -978,11 +1308,13 @@ even when the base checkout uses sparse settings. Confirmation retries retain
|
|
|
978
1308
|
local context. Files, nested clones and administration inside the owned PR
|
|
979
1309
|
worktree are disposable; cleanup does not inventory their external consumers.
|
|
980
1310
|
Other PR worktrees and retained sessions remain separate. Cleanup rechecks remote
|
|
981
|
-
closure before removal. The [exclusive-environment decision](../../.agents/notes/
|
|
982
|
-
|
|
1311
|
+
closure before removal. The [exclusive-environment decision](../../.agents/notes/archived/architecture/2026-10-17-exclusive-review-environment.md)
|
|
1312
|
+
records the choice of this ownership boundary.
|
|
983
1313
|
|
|
984
|
-
|
|
985
|
-
|
|
1314
|
+
The [review architecture](../../docs/design/daynight-review.md#worktree-生命周期)
|
|
1315
|
+
defines target validation and recovery boundaries; the
|
|
1316
|
+
[worktree ownership decision](../../.agents/notes/archived/architecture/2026-10-17-owned-review-worktrees.md)
|
|
1317
|
+
records their rationale.
|
|
986
1318
|
|
|
987
1319
|
## Copilot execution
|
|
988
1320
|
|
|
@@ -1102,17 +1434,17 @@ before completing the round. It owns scheduling and final state transitions;
|
|
|
1102
1434
|
runtime process supervision supplies evidence under the foreground execution
|
|
1103
1435
|
contract.
|
|
1104
1436
|
|
|
1105
|
-
The [execution decision](../../.agents/notes/
|
|
1437
|
+
The [execution decision](../../.agents/notes/archived/architecture/2026-10-17-copilot-session-execution.md)
|
|
1106
1438
|
records process and publication boundaries; the
|
|
1107
|
-
[PR-quality decision](../../.agents/notes/
|
|
1439
|
+
[PR-quality decision](../../.agents/notes/archived/process/2026-10-21-review-pr-quality-gates.md)
|
|
1108
1440
|
records the approval policy, and the
|
|
1109
1441
|
[multi-perspective decision](../../.agents/notes/implemented/process/2026-10-22-pr-specific-review-perspectives.md)
|
|
1110
1442
|
records delegation and synthesis. The
|
|
1111
|
-
[conversation-cycle decision](../../.agents/notes/
|
|
1443
|
+
[conversation-cycle decision](../../.agents/notes/archived/architecture/2026-10-21-review-conversation-cycle.md)
|
|
1112
1444
|
records durable follow-ups and publication verification. The
|
|
1113
1445
|
[skill design](../../docs/design/daynight-review-skill.md) owns packaging, snapshots and
|
|
1114
1446
|
loading, with rationale in the
|
|
1115
|
-
[bundled-skill decision](../../.agents/notes/
|
|
1447
|
+
[bundled-skill decision](../../.agents/notes/archived/architecture/2026-10-20-bundled-review-skill.md).
|
|
1116
1448
|
Native probes with Copilot CLI 1.0.100 verify actual bundled-skill activation and
|
|
1117
1449
|
changed-bundle resume with the same UUID, including comma, space and Unicode
|
|
1118
1450
|
paths. The bundled-skill decision records the probe's conditions and limits.
|
|
@@ -1171,7 +1503,7 @@ and logs. That explicitly confirmed restart reconciles interrupted work with
|
|
|
1171
1503
|
the same captured target and session; it never declares a saved running attempt
|
|
1172
1504
|
complete or kills a saved process ID.
|
|
1173
1505
|
|
|
1174
|
-
The [coordination decision](../../.agents/notes/
|
|
1506
|
+
The [coordination decision](../../.agents/notes/archived/architecture/2026-10-17-foreground-review-coordination.md)
|
|
1175
1507
|
explains scheduling and the foreground execution boundary. The
|
|
1176
|
-
[stale-lock recovery decision](../../.agents/notes/
|
|
1508
|
+
[stale-lock recovery decision](../../.agents/notes/archived/bug-fix/2026-10-18-stale-instance-lock-recovery.md)
|
|
1177
1509
|
records owner-liveness checks and the separate process-exclusion requirement.
|
package/dist/api/client.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import type { Operation } from "./operation.js";
|
|
2
|
-
import type { AttachmentConsumer, CreateProjectInput, CreateTaskInput, DeleteTaskInput, ErrorDetails, Project, PutTaskAttachmentInput, ReadyTaskFilters, ServerError, Task, SetTaskStatusInput, TaskAttachment, TaskFilters, TaskGraph, UpdateTaskInput, ClaimWorkerTaskInput, CompleteWorkerTaskInput, ReleaseWorkerClaimInput, ResumeWorkerTaskInput, TransferWorkerClaimInput, UpdateWorkerClaimInput, Page, TaskPageQuery } from "./types.js";
|
|
2
|
+
import type { AttachmentConsumer, CreateProjectInput, CreateTaskInput, DeleteTaskInput, ErrorDetails, Project, ProjectMember, PutTaskAttachmentInput, ReadyTaskFilters, ServerError, Task, SetTaskStatusInput, TaskAttachment, TaskFilters, TaskGraph, UpdateTaskInput, ClaimWorkerTaskInput, CompleteWorkerTaskInput, ReleaseWorkerClaimInput, ResumeWorkerTaskInput, TransferWorkerClaimInput, UpdateWorkerClaimInput, User, Page, TaskPageQuery } from "./types.js";
|
|
3
3
|
type Context = {
|
|
4
4
|
readonly operation: string;
|
|
5
5
|
readonly projectId?: string;
|
|
@@ -26,9 +26,11 @@ export declare class ApiError extends Error {
|
|
|
26
26
|
});
|
|
27
27
|
}
|
|
28
28
|
export type ApiClient = {
|
|
29
|
+
getCurrentUser(): Promise<User>;
|
|
29
30
|
createProject(input: CreateProjectInput): Promise<Project>;
|
|
30
31
|
getProject(projectId: string): Promise<Project>;
|
|
31
32
|
listProjects(): Promise<readonly Project[]>;
|
|
33
|
+
listProjectMembers(projectId: string): Promise<readonly ProjectMember[]>;
|
|
32
34
|
createTask(projectId: string, input: CreateTaskInput): Promise<Task>;
|
|
33
35
|
getTask(projectId: string, taskId: string): Promise<Task>;
|
|
34
36
|
listTasks(projectId: string, filters?: TaskFilters): Promise<readonly Task[]>;
|
|
@@ -52,6 +54,7 @@ export type ApiClient = {
|
|
|
52
54
|
export declare const createApiClient: (options: {
|
|
53
55
|
readonly serverUrl: string;
|
|
54
56
|
readonly serverToken?: string;
|
|
57
|
+
readonly expectedUserId?: string;
|
|
55
58
|
readonly operation: Operation;
|
|
56
59
|
readonly fetch?: typeof globalThis.fetch;
|
|
57
60
|
}) => ApiClient;
|
package/dist/api/client.js
CHANGED
|
@@ -2,7 +2,7 @@ import { performance } from "node:perf_hooks";
|
|
|
2
2
|
import { parseApiJson, stringifyApiJson } from "./json.js";
|
|
3
3
|
import { OperationError } from "./operation.js";
|
|
4
4
|
import { validateServerToken, validateTokenTransport } from "../config/server-token.js";
|
|
5
|
-
import { canonicalId, parsePage, parseProject, parseServerError, parseTask, parseTaskGraph, parseTaskAttachment, ProtocolError, validateAttachmentPath } from "./parse.js";
|
|
5
|
+
import { canonicalId, parsePage, parseProject, parseProjectMembers, parseServerError, parseTask, parseTaskGraph, parseTaskAttachment, parseUser, ProtocolError, validateAttachmentPath } from "./parse.js";
|
|
6
6
|
export class ApiError extends Error {
|
|
7
7
|
operation;
|
|
8
8
|
phase;
|
|
@@ -55,6 +55,7 @@ export const createApiClient = (options) => {
|
|
|
55
55
|
if (!/^https?:$/.test(origin.protocol) || origin.username !== "" || origin.password !== "" || origin.pathname !== "/" || origin.search !== "" || origin.hash !== "")
|
|
56
56
|
throw new Error("serverUrl must be an HTTP(S) service origin without credentials, path, query or fragment.");
|
|
57
57
|
const serverToken = options.serverToken === undefined ? undefined : validateServerToken(options.serverToken);
|
|
58
|
+
const expectedUserId = options.expectedUserId === undefined ? undefined : resourceId(options.expectedUserId);
|
|
58
59
|
if (serverToken !== undefined)
|
|
59
60
|
validateTokenTransport(origin.origin);
|
|
60
61
|
const operation = options.operation;
|
|
@@ -166,6 +167,15 @@ export const createApiClient = (options) => {
|
|
|
166
167
|
reader = response.body.getReader();
|
|
167
168
|
// Cancelling an already errored stream repeats its existing failure, rather than introducing a cleanup failure.
|
|
168
169
|
void reader.closed.catch((error) => { bodyFailure = error; });
|
|
170
|
+
}
|
|
171
|
+
if (success && expectedUserId !== undefined) {
|
|
172
|
+
phase = "protocol";
|
|
173
|
+
const principal = response.headers.get("Daynight-User-ID");
|
|
174
|
+
if (principal === null || canonicalId(principal) !== expectedUserId)
|
|
175
|
+
throw new ProtocolError("The authenticated response principal does not match the expected user.");
|
|
176
|
+
phase = "response";
|
|
177
|
+
}
|
|
178
|
+
if (reader !== undefined) {
|
|
169
179
|
while (true) {
|
|
170
180
|
checkRequest();
|
|
171
181
|
const chunk = await Promise.race([reader.read(), aborted]);
|
|
@@ -344,6 +354,8 @@ export const createApiClient = (options) => {
|
|
|
344
354
|
const herdrMatches = (actual, expected) => actual === null || expected === null ? actual === expected : actual.session === expected.session && actual.workspaceId === expected.workspaceId && actual.paneId === expected.paneId;
|
|
345
355
|
const descriptorMatches = (worker, descriptor) => worker.claimId === canonicalId(descriptor.claimId) && worker.workerId === canonicalId(descriptor.workerId) && worker.machine.id === canonicalId(descriptor.machine.id) && worker.machine.name === descriptor.machine.name && worker.platform === descriptor.platform && worker.agent === descriptor.agent && worker.worktreeId === canonicalId(descriptor.worktreeId);
|
|
346
356
|
const workerMutation = (projectId, taskId, action, suffix, method, input, matches, sameValue = false) => {
|
|
357
|
+
if (Object.hasOwn(input, "continuityConfirmed"))
|
|
358
|
+
throw new Error("continuityConfirmed is no longer accepted. New executions require fresh claim and worktree IDs.");
|
|
347
359
|
const project = resourceId(projectId), task = resourceId(taskId);
|
|
348
360
|
taskVersion(input.version);
|
|
349
361
|
return exchange({ operation: action, projectId: project, taskId: task }, `/projects/${encodeURIComponent(project)}/tasks/${encodeURIComponent(task)}${suffix}`, method, { kind: "json", parse: (value) => {
|
|
@@ -355,12 +367,17 @@ export const createApiClient = (options) => {
|
|
|
355
367
|
} }, [200], { kind: "json", value: input }, true);
|
|
356
368
|
};
|
|
357
369
|
return {
|
|
370
|
+
getCurrentUser: () => exchange({ operation: "auth.me" }, "/me", "GET", { kind: "json", parse: parseUser }, [200], undefined, true),
|
|
358
371
|
createProject: (input) => request({ operation: "project.create" }, "/projects", "POST", (value) => parseProject(value), { name: input.name, repoUrl: input.repoUrl }),
|
|
359
372
|
getProject: (projectId) => {
|
|
360
373
|
const project = resourceId(projectId);
|
|
361
374
|
return request({ operation: "project.show", projectId: project }, `/projects/${encodeURIComponent(project)}`, "GET", (value) => parseProject(value, project));
|
|
362
375
|
},
|
|
363
376
|
listProjects: () => list({ operation: "project.list" }, "/projects", (value) => parseProject(value), (project) => project.id),
|
|
377
|
+
listProjectMembers: (projectId) => {
|
|
378
|
+
const project = resourceId(projectId);
|
|
379
|
+
return exchange({ operation: "project.members", projectId: project }, `/projects/${encodeURIComponent(project)}/members`, "GET", { kind: "json", parse: (value) => parseProjectMembers(value, project) }, [200], undefined, true);
|
|
380
|
+
},
|
|
364
381
|
createTask: (projectId, input) => {
|
|
365
382
|
const project = resourceId(projectId);
|
|
366
383
|
writableProperties(input.properties);
|