Files
paperclip/packages/shared/src/validators/index.ts
T
Aron Prins 70b1a9109d Improve CLI API parity coverage (#6626)
## Thinking Path

> - Paperclip is a control plane for AI-agent companies, with the CLI
acting as a scriptable operator and agent interface to that control
plane.
> - The REST API surface has grown across companies, agents, issues,
routines, plugins, auth, workspaces, secrets, and operational inspection
commands.
> - The CLI had drifted from that API surface: some commands were
missing, some command shapes differed from docs/reference material, and
several edge cases only failed during end-to-end local-source testing.
> - The local development runbook requires these tests to be disposable
and isolated from a real `~/.paperclip`, `~/.codex`, or `~/.claude`
installation.
> - This pull request adds broad CLI/API parity coverage, fixes the
actionable bugs found during that pass, and records the reproducible
test log under `doc/logs`.
> - The benefit is a more complete, scriptable CLI surface with
regression coverage for the command families exercised by the parity
run.

## What Changed

- Added or expanded CLI command coverage for access/auth, companies,
agents, projects, goals, issues and subresources, routines, plugins,
workspaces, activity/run/cost/dashboard inspection, assets, skills,
secrets, tokens, prompt/wake flows, and local setup helpers.
- Fixed CLI/API parity bugs found during the run, including context
profile patching, issue interaction optional payloads, malformed
tree-hold errors, environment duplicate handling, configure
invalid-section exit codes, worktree pnpm invocation, token agent ID
resolution, plugin tool worker lookup, and routine webhook secret
cleanup.
- Added missing CLI wrappers and route coverage for health/access,
invite resolution URL forwarding, join status normalization, secret
lifecycle commands, LLM docs routes, available-skill isolation, positive
board-claim coverage, and interactive `connect` prompt-flow tests.
- Added a schema-backed `/api/openapi.json` route sufficient for CLI
parity and `paperclipai openapi --json` smoke coverage.
- Added `doc/logs/2026-05-24-cli-api-parity-e2e-log.md` with the
detailed living test/bug log and renamed the log directory from
`doc/bugs` to `doc/logs`.
- Added `doc/plans/2026-05-23-cli-api-parity.md` and the OpenAPI parity
reference used during the pass.

OpenAPI note: this PR intentionally does not try to subsume
`feature/openapi-spec`. The OpenAPI implementation here is schema-backed
and better than the earlier route-inventory stub, but
`feature/openapi-spec` is the fuller/better OpenAPI branch because it
includes exact mounted-route coverage tests and additional current route
coverage. That branch should stay as its own PR and can supersede this
OpenAPI route implementation.

## Verification

Targeted automated checks run:

- `pnpm exec vitest run server/src/__tests__/openapi-routes.test.ts`
- `pnpm exec vitest run server/src/__tests__/board-claim.test.ts`
- `pnpm exec vitest run cli/src/__tests__/connect.test.ts`
- `pnpm exec vitest run cli/src/__tests__/agent-lifecycle.test.ts`
- `pnpm exec vitest run server/src/__tests__/plugin-database.test.ts`
- `pnpm exec vitest run server/src/__tests__/routines-service.test.ts`
- `pnpm --dir cli typecheck`
- `pnpm --dir server typecheck`

Manual/local E2E verification:

- Ran the full disposable local-source CLI/API parity pass with isolated
`PAPERCLIP_HOME`, `PAPERCLIP_CONFIG`, `PAPERCLIP_CONTEXT`,
`PAPERCLIP_AUTH_STORE`, `CODEX_HOME`, and `CLAUDE_HOME` under
`tmp/cli-api-parity`.
- Verified `DATABASE_URL` and `DATABASE_MIGRATION_URL` stayed unset for
the scratch server.
- Verified live health and schema-backed OpenAPI responses on
non-default port `3197`.
- Revoked created board/agent tokens and cleaned up temporary plugins,
secrets, non-default environments, and project workspaces.
- See `doc/logs/2026-05-24-cli-api-parity-e2e-log.md` for the full
command-by-command reproduction log.

Not run:

- Full `pnpm test`, `pnpm test:run`, or `pnpm build` were not run after
the entire branch because the branch is broad and the parity pass used
focused test/typecheck verification plus live isolated CLI reruns.

## Risks

- This is a broad PR and touches many CLI command modules, so review
surface is high. The changes are grouped around one theme, but a split
may be easier if maintainers prefer narrower PRs.
- The OpenAPI route in this PR is not the final/best OpenAPI
implementation. `feature/openapi-spec` has stronger exact-route coverage
and should remain the source for the dedicated OpenAPI PR.
- The living log is intentionally detailed and large. It is useful for
reproducibility but adds documentation weight.
- No UI changes are intended; screenshots are not applicable.

> For core feature work, check [`ROADMAP.md`](ROADMAP.md) first and
discuss it in `#dev` before opening the PR. Feature PRs that overlap
with planned core work may need to be redirected — check the roadmap
first. See `CONTRIBUTING.md`.

## Model Used

- OpenAI Codex, GPT-5-based coding agent in Codex desktop. Exact served
model/context-window identifier was not exposed in the local app. Work
used shell/Git/GitHub CLI tooling, local source inspection, targeted
test execution, and live isolated Paperclip CLI/API smoke testing.

## Checklist

- [x] I have included a thinking path that traces from project context
to this change
- [x] I have specified the model used (with version and capability
details)
- [x] I have checked ROADMAP.md and confirmed this PR does not duplicate
planned core work
- [x] I have run tests locally and they pass
- [x] I have added or updated tests where applicable
- [x] If this change affects the UI, I have included before/after
screenshots
- [x] I have updated relevant documentation to reflect my changes
- [x] I have considered and documented any risks above
- [x] I will address all Greptile and reviewer comments before
requesting merge

---------

Co-authored-by: Devin Foley <devin@devinfoley.com>
2026-06-02 17:13:29 -07:00

482 lines
14 KiB
TypeScript

export {
instanceGeneralSettingsSchema,
patchInstanceGeneralSettingsSchema,
type InstanceGeneralSettings,
type PatchInstanceGeneralSettings,
instanceExperimentalSettingsSchema,
patchInstanceExperimentalSettingsSchema,
issueGraphLivenessAutoRecoveryRequestSchema,
type InstanceExperimentalSettings,
type PatchInstanceExperimentalSettings,
type IssueGraphLivenessAutoRecoveryRequest,
} from "./instance.js";
export {
upsertBudgetPolicySchema,
resolveBudgetIncidentSchema,
type UpsertBudgetPolicy,
type ResolveBudgetIncident,
} from "./budget.js";
export {
createCompanySchema,
updateCompanySchema,
updateCompanyBrandingSchema,
type CreateCompany,
type UpdateCompany,
type UpdateCompanyBranding,
} from "./company.js";
export {
environmentDriverSchema,
environmentStatusSchema,
environmentLeaseStatusSchema,
environmentLeaseCleanupStatusSchema,
createEnvironmentSchema,
updateEnvironmentSchema,
probeEnvironmentConfigSchema,
type CreateEnvironment,
type UpdateEnvironment,
type ProbeEnvironmentConfig,
} from "./environment.js";
export {
feedbackDataSharingPreferenceSchema,
feedbackTargetTypeSchema,
feedbackTraceStatusSchema,
feedbackVoteValueSchema,
upsertIssueFeedbackVoteSchema,
type UpsertIssueFeedbackVote,
} from "./feedback.js";
export {
sidebarOrderPreferenceSchema,
upsertSidebarOrderPreferenceSchema,
type UpsertSidebarOrderPreference,
} from "./sidebar-preferences.js";
export {
resourceMembershipStateSchema,
updateResourceMembershipSchema,
type UpdateResourceMembership,
} from "./resource-memberships.js";
export {
companySkillSourceTypeSchema,
companySkillTrustLevelSchema,
companySkillCompatibilitySchema,
companySkillSourceBadgeSchema,
companySkillFileInventoryEntrySchema,
companySkillSchema,
companySkillListItemSchema,
companySkillUsageAgentSchema,
companySkillDetailSchema,
companySkillUpdateStatusSchema,
companySkillAuditFindingSchema,
companySkillAuditResultSchema,
companySkillImportSchema,
companySkillProjectScanRequestSchema,
companySkillProjectScanSkippedSchema,
companySkillProjectScanConflictSchema,
companySkillProjectScanResultSchema,
companySkillCreateSchema,
companySkillFileDetailSchema,
companySkillFileUpdateSchema,
catalogSkillKindSchema,
catalogSkillFileSchema,
catalogSkillSchema,
catalogSkillListQuerySchema,
catalogSkillFileDetailSchema,
companySkillInstallCatalogSchema,
companySkillInstallCatalogResultSchema,
companySkillInstallUpdateSchema,
companySkillResetSchema,
type CompanySkillImport,
type CompanySkillProjectScan,
type CompanySkillCreate,
type CompanySkillFileUpdate,
type CatalogSkillListQuery,
type CompanySkillInstallCatalog,
type CompanySkillInstallUpdate,
type CompanySkillReset,
} from "./company-skill.js";
export {
agentSkillStateSchema,
agentSkillSyncModeSchema,
agentSkillEntrySchema,
agentSkillSnapshotSchema,
agentSkillSyncSchema,
type AgentSkillSync,
} from "./adapter-skills.js";
export {
portabilityIncludeSchema,
portabilityEnvInputSchema,
portabilityCompanyManifestEntrySchema,
portabilitySidebarOrderSchema,
portabilityAgentManifestEntrySchema,
portabilitySkillManifestEntrySchema,
portabilityManifestSchema,
portabilitySourceSchema,
portabilityTargetSchema,
portabilityAgentSelectionSchema,
portabilityCollisionStrategySchema,
companyPortabilityExportSchema,
companyPortabilityPreviewSchema,
companyPortabilityImportSchema,
type CompanyPortabilityExport,
type CompanyPortabilityPreview,
type CompanyPortabilityImport,
} from "./company-portability.js";
export {
createAgentSchema,
createAgentHireSchema,
updateAgentSchema,
agentRuntimeConfigSchema,
agentInstructionsBundleModeSchema,
updateAgentInstructionsBundleSchema,
upsertAgentInstructionsFileSchema,
updateAgentInstructionsPathSchema,
createAgentKeySchema,
agentMineInboxQuerySchema,
wakeAgentSchema,
resetAgentSessionSchema,
testAdapterEnvironmentSchema,
agentPermissionsSchema,
updateAgentPermissionsSchema,
type CreateAgent,
type CreateAgentHire,
type UpdateAgent,
type UpdateAgentInstructionsBundle,
type UpsertAgentInstructionsFile,
type UpdateAgentInstructionsPath,
type CreateAgentKey,
type AgentMineInboxQuery,
type WakeAgent,
type ResetAgentSession,
type TestAdapterEnvironment,
type UpdateAgentPermissions,
} from "./agent.js";
export {
createProjectSchema,
updateProjectSchema,
createProjectWorkspaceSchema,
updateProjectWorkspaceSchema,
projectExecutionWorkspacePolicySchema,
projectWorkspaceRuntimeConfigSchema,
type CreateProject,
type UpdateProject,
type CreateProjectWorkspace,
type UpdateProjectWorkspace,
type ProjectExecutionWorkspacePolicy,
} from "./project.js";
export {
createDocumentAnnotationCommentSchema,
createDocumentAnnotationThreadSchema,
documentAnnotationAnchorConfidenceSchema,
documentAnnotationAnchorSelectorSchema,
documentAnnotationAnchorStateSchema,
documentAnnotationTextPositionSelectorSchema,
documentAnnotationTextQuoteSelectorSchema,
documentAnnotationThreadStatusSchema,
updateDocumentAnnotationThreadSchema,
type CreateDocumentAnnotationComment,
type CreateDocumentAnnotationThread,
type UpdateDocumentAnnotationThread,
} from "./document-annotation.js";
export {
createIssueSchema,
createIssueInputSchema,
createChildIssueSchema,
createAcceptedPlanDecompositionSchema,
resolveCreateIssueStatusDefault,
createIssueLabelSchema,
issueBlockedInboxAttentionSchema,
issueBlockedInboxIssueRefSchema,
issueBlockedInboxReasonSchema,
issueBlockedInboxSeveritySchema,
issueBlockedInboxStateSchema,
updateIssueSchema,
issueExecutionPolicySchema,
issueExecutionStateSchema,
issueRecoveryActionReadModelSchema,
resolveIssueRecoveryActionSchema,
issueReviewRequestSchema,
issueExecutionWorkspaceSettingsSchema,
checkoutIssueSchema,
issueCommentAuthorTypeSchema,
issueCommentPresentationSchema,
issueCommentMetadataRowSchema,
issueCommentMetadataSectionSchema,
issueCommentMetadataSchema,
addIssueCommentSchema,
issueThreadInteractionStatusSchema,
issueThreadInteractionKindSchema,
issueThreadInteractionContinuationPolicySchema,
suggestedTaskDraftSchema,
suggestTasksPayloadSchema,
suggestTasksResultCreatedTaskSchema,
suggestTasksResultSchema,
askUserQuestionsQuestionOptionSchema,
askUserQuestionsQuestionSchema,
askUserQuestionsPayloadSchema,
askUserQuestionsAnswerSchema,
askUserQuestionsResultSchema,
requestConfirmationIssueDocumentTargetSchema,
requestConfirmationCustomTargetSchema,
requestConfirmationTargetSchema,
requestConfirmationPayloadSchema,
requestConfirmationResultSchema,
createIssueThreadInteractionSchema,
acceptIssueThreadInteractionSchema,
rejectIssueThreadInteractionSchema,
cancelIssueThreadInteractionSchema,
respondIssueThreadInteractionSchema,
linkIssueApprovalSchema,
createIssueAttachmentMetadataSchema,
issueDocumentFormatSchema,
issueDocumentKeySchema,
upsertIssueDocumentSchema,
restoreIssueDocumentRevisionSchema,
type CreateIssue,
type CreateChildIssue,
type CreateAcceptedPlanDecomposition,
type CreateIssueLabel,
type UpdateIssue,
type IssueExecutionWorkspaceSettings,
type IssueRecoveryActionReadModel,
type ResolveIssueRecoveryAction,
type CheckoutIssue,
type AddIssueComment,
type CreateIssueThreadInteraction,
type AcceptIssueThreadInteraction,
type RejectIssueThreadInteraction,
type CancelIssueThreadInteraction,
type RespondIssueThreadInteraction,
type LinkIssueApproval,
type CreateIssueAttachmentMetadata,
type IssueDocumentFormat,
type UpsertIssueDocument,
type RestoreIssueDocumentRevision,
} from "./issue.js";
export {
COMPANY_SEARCH_DEFAULT_LIMIT,
COMPANY_SEARCH_MAX_LIMIT,
COMPANY_SEARCH_MAX_OFFSET,
COMPANY_SEARCH_MAX_QUERY_LENGTH,
COMPANY_SEARCH_MAX_TOKENS,
companySearchQuerySchema,
type CompanySearchQuery,
} from "./search.js";
export {
createIssueTreeHoldSchema,
issueTreeControlModeSchema,
issueTreeHoldReleasePolicySchema,
previewIssueTreeControlSchema,
releaseIssueTreeHoldSchema,
type CreateIssueTreeHold,
type PreviewIssueTreeControl,
type ReleaseIssueTreeHold,
} from "./issue-tree-control.js";
export {
createIssueWorkProductSchema,
updateIssueWorkProductSchema,
attachmentArtifactWorkProductMetadataSchema,
issueWorkProductTypeSchema,
issueWorkProductStatusSchema,
issueWorkProductReviewStateSchema,
type CreateIssueWorkProduct,
type UpdateIssueWorkProduct,
} from "./work-product.js";
export {
executionWorkspaceConfigSchema,
updateExecutionWorkspaceSchema,
executionWorkspaceStatusSchema,
executionWorkspaceCloseActionKindSchema,
executionWorkspaceCloseActionSchema,
executionWorkspaceCloseGitReadinessSchema,
executionWorkspaceCloseLinkedIssueSchema,
executionWorkspaceCloseReadinessSchema,
executionWorkspaceCloseReadinessStateSchema,
type UpdateExecutionWorkspace,
} from "./execution-workspace.js";
export {
createGoalSchema,
updateGoalSchema,
type CreateGoal,
type UpdateGoal,
} from "./goal.js";
export {
createApprovalSchema,
resolveApprovalSchema,
requestApprovalRevisionSchema,
resubmitApprovalSchema,
addApprovalCommentSchema,
type CreateApproval,
type ResolveApproval,
type RequestApprovalRevision,
type ResubmitApproval,
type AddApprovalComment,
} from "./approval.js";
export {
envBindingPlainSchema,
envBindingSecretRefSchema,
envBindingSchema,
envConfigSchema,
createSecretSchema,
createSecretProviderConfigSchema,
updateSecretProviderConfigSchema,
secretProviderConfigDiscoveryPreviewSchema,
remoteSecretImportPreviewSchema,
remoteSecretImportSchema,
remoteSecretImportSelectionSchema,
localEncryptedProviderConfigSchema,
awsSecretsManagerProviderConfigSchema,
gcpSecretManagerProviderConfigSchema,
vaultProviderConfigSchema,
secretProviderConfigPayloadSchema,
createSecretBindingSchema,
rotateSecretSchema,
secretBindingTargetSchema,
updateSecretSchema,
type CreateSecretBinding,
type CreateSecret,
type CreateSecretProviderConfig,
type UpdateSecretProviderConfig,
type SecretProviderConfigDiscoveryPreview,
type RemoteSecretImportPreview,
type RemoteSecretImport,
type RemoteSecretImportSelection,
type RotateSecret,
type UpdateSecret,
} from "./secret.js";
export {
createRoutineSchema,
updateRoutineSchema,
createRoutineTriggerSchema,
updateRoutineTriggerSchema,
routineVariableSchema,
routineRevisionSnapshotRoutineV1Schema,
routineRevisionSnapshotTriggerV1Schema,
routineRevisionSnapshotV1Schema,
routineRevisionSnapshotSchema,
runRoutineSchema,
rotateRoutineTriggerSecretSchema,
type CreateRoutine,
type UpdateRoutine,
type CreateRoutineTrigger,
type UpdateRoutineTrigger,
type RunRoutine,
type RotateRoutineTriggerSecret,
} from "./routine.js";
export {
createCostEventSchema,
updateBudgetSchema,
type CreateCostEvent,
type UpdateBudget,
} from "./cost.js";
export {
createFinanceEventSchema,
type CreateFinanceEvent,
} from "./finance.js";
export {
createAssetImageMetadataSchema,
type CreateAssetImageMetadata,
} from "./asset.js";
export {
createCompanyInviteSchema,
createOpenClawInvitePromptSchema,
acceptInviteSchema,
listCompanyInvitesQuerySchema,
listJoinRequestsQuerySchema,
claimJoinRequestApiKeySchema,
boardCliAuthAccessLevelSchema,
createCliAuthChallengeSchema,
resolveCliAuthChallengeSchema,
createBoardApiKeySchema,
currentUserProfileSchema,
authSessionSchema,
updateCurrentUserProfileSchema,
updateCompanyMemberSchema,
updateCompanyMemberWithPermissionsSchema,
archiveCompanyMemberSchema,
updateMemberPermissionsSchema,
searchAdminUsersQuerySchema,
updateUserCompanyAccessSchema,
type CreateCompanyInvite,
type CreateOpenClawInvitePrompt,
type AcceptInvite,
type ListCompanyInvitesQuery,
type ListJoinRequestsQuery,
type ClaimJoinRequestApiKey,
type BoardCliAuthAccessLevel,
type CreateCliAuthChallenge,
type ResolveCliAuthChallenge,
type CreateBoardApiKey,
type CurrentUserProfile,
type AuthSession,
type UpdateCurrentUserProfile,
type UpdateCompanyMember,
type UpdateCompanyMemberWithPermissions,
type ArchiveCompanyMember,
type UpdateMemberPermissions,
type SearchAdminUsersQuery,
type UpdateUserCompanyAccess,
} from "./access.js";
export {
jsonSchemaSchema,
pluginJobDeclarationSchema,
pluginWebhookDeclarationSchema,
pluginToolDeclarationSchema,
pluginEnvironmentDriverDeclarationSchema,
pluginUiSlotDeclarationSchema,
pluginLauncherActionDeclarationSchema,
pluginLauncherRenderDeclarationSchema,
pluginLauncherDeclarationSchema,
pluginDatabaseDeclarationSchema,
pluginManagedSkillFileDeclarationSchema,
pluginManagedSkillDeclarationSchema,
pluginApiRouteDeclarationSchema,
pluginManifestV1Schema,
installPluginSchema,
upsertPluginConfigSchema,
patchPluginConfigSchema,
updatePluginStatusSchema,
uninstallPluginSchema,
pluginStateScopeKeySchema,
setPluginStateSchema,
listPluginStateSchema,
type PluginJobDeclarationInput,
type PluginWebhookDeclarationInput,
type PluginToolDeclarationInput,
type PluginEnvironmentDriverDeclarationInput,
type PluginUiSlotDeclarationInput,
type PluginLauncherActionDeclarationInput,
type PluginLauncherRenderDeclarationInput,
type PluginLauncherDeclarationInput,
type PluginDatabaseDeclarationInput,
type PluginManagedSkillFileDeclarationInput,
type PluginManagedSkillDeclarationInput,
type PluginApiRouteDeclarationInput,
type PluginManifestV1Input,
type InstallPlugin,
type UpsertPluginConfig,
type PatchPluginConfig,
type UpdatePluginStatus,
type UninstallPlugin,
type PluginStateScopeKey,
type SetPluginState,
type ListPluginState,
} from "./plugin.js";