Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
50 changes: 50 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,56 @@ Format: [Keep a Changelog](https://keepachangelog.com/en/1.1.0/) · Versioning:

## [Unreleased]

### Changed
- Upgraded all templates to `@objectstack/* ^7.4.1` (from `^7.3.0`).
- **Approvals migrated to the 7.4.x flow-node model (ADR-0019).** The standalone
`ApprovalProcess` export and the stack-level `approvals:` key were removed in
7.4.x; approvals are now an `approval` node on a `record_change` flow whose
`approve` / `reject` out-edges carry the decision branches. Reworked
`packages/expense` (`expense_approval.flow.ts`) and `packages/content`
(`publish_approval.flow.ts`) accordingly and deleted their `src/approvals/`
directories.
- **Repaired `packages/project`** (previously did not typecheck): rewrote both
state machines to the canonical `StateMachineConfig` (XState) shape and
`stateMachines: { lifecycle }` wiring; fixed flow `type: 'scheduled'` →
`'schedule'` and converted condition-node out-edges to
`type: 'conditional'` + `condition` / `isDefault`; moved view `filter` out of
the `data` provider to the view-level array form; normalised ESM relative
imports to `.js`; and wired the three flows back into the stack.

- **Flow capability re-evaluation against the 7.4.x node registry.**
- Notifications now use the real builtin **`notify`** node (delivers via the
messaging service — inbox/email/push) instead of `script` +
`actionType: 'notification'`, which the 7.4.x script executor treats as a
**no-op** (log only). Migrated all 21 notification nodes + 2 templated-email
nodes (`actionType: 'email'`, also a log-only stub → `notify` with
`channels: ['email']`) across todo, expense, content, contracts, helpdesk,
hr, procurement, compliance, project. `link:` → `actionUrl:` to match the
`notify` config.
- `packages/project` flows used node types with **no runtime executor**
(`query`, `foreach`, `condition`) — they built but could never run. Rewrote
to the registered builtins (`get_record`, `loop`, `decision`) with
object-form filters, and wired the three flows into the stack. (The AI /
scheduled-scan logic in these flows remains a documented v0 stub:
`invoke_function` targets and per-item iteration depend on engine features
not yet wired.)

- **QA scenario fixtures rewritten + runnable.** `packages/todo` and
`packages/hr` shipped obsolete `qa/*.test.json` (both were copies of an old
todo suite targeting removed objects `project`/`task`/`task_label`). Rewrote
them against the real schemas (todo: `todo_task`/`todo_label` lifecycle,
labels, due-date round-trip; hr: `hr_employee` onboarding, `hr_time_off_request`
draft→submitted→approved, `hr_document`). Added `scripts/run-qa.mjs`, a small
runner that authenticates (better-auth sign-up) and executes the scenarios
against the versioned data API — needed because the `objectstack test` adapter
bundled in `@objectstack/core` 7.4.x targets `/api/data/<object>` while the
7.4.x REST plugin serves `/api/v1/data/<object>` (so the bundled runner 404s).
Both suites pass green (`pnpm --filter @objectlab/<todo|hr> test:qa` against a
running `objectstack dev`). Each template's `test` script now runs
`objectstack build` (the schema/protocol validation gate).

All nine templates pass `tsc --noEmit` and `objectstack build` on 7.4.1.

### Added
- `packages/expense` — employee expense & reimbursement template (v0). 3
objects (`report`, `line`, `category`), report lifecycle state machine
Expand Down
24 changes: 12 additions & 12 deletions packages/compliance/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,20 +15,20 @@
"start": "objectstack start -p 4005",
"build": "objectstack build",
"typecheck": "tsc --noEmit",
"test": "objectstack test"
"test": "objectstack build"
},
"dependencies": {
"@objectstack/account": "^7.3.0",
"@objectstack/cli": "^7.3.0",
"@objectstack/driver-memory": "^7.3.0",
"@objectstack/driver-sql": "^7.3.0",
"@objectstack/driver-sqlite-wasm": "^7.3.0",
"@objectstack/metadata": "^7.3.0",
"@objectstack/objectql": "^7.3.0",
"@objectstack/runtime": "^7.3.0",
"@objectstack/service-analytics": "^7.3.0",
"@objectstack/service-automation": "^7.3.0",
"@objectstack/spec": "^7.3.0",
"@objectstack/account": "^7.4.1",
"@objectstack/cli": "^7.4.1",
"@objectstack/driver-memory": "^7.4.1",
"@objectstack/driver-sql": "^7.4.1",
"@objectstack/driver-sqlite-wasm": "^7.4.1",
"@objectstack/metadata": "^7.4.1",
"@objectstack/objectql": "^7.4.1",
"@objectstack/runtime": "^7.4.1",
"@objectstack/service-analytics": "^7.4.1",
"@objectstack/service-automation": "^7.4.1",
"@objectstack/spec": "^7.4.1",
"sql.js": "^1.14.1"
},
"optionalDependencies": {
Expand Down
3 changes: 1 addition & 2 deletions packages/compliance/src/flows/evidence_auto_expire.flow.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,7 @@ export const EvidenceAutoExpireFlow: Flow = {
label: 'Start',
config: {
objectName: 'compliance_evidence',
criteria:
'status == "approved" && expires_on != null && expires_on == daysAgo(0)',
criteria: 'status == "approved" && expires_on != null && expires_on == daysAgo(0)',
criteriaDialect: 'cel',
},
},
Expand Down
8 changes: 3 additions & 5 deletions packages/compliance/src/flows/evidence_expiring.flow.ts
Original file line number Diff line number Diff line change
Expand Up @@ -40,15 +40,13 @@ export const EvidenceExpiringFlow: Flow = {
},
{
id: 'notify',
type: 'script',
type: 'notify',
label: 'Notify Collector',
config: {
actionType: 'notification',
recipients: ['{ev.collected_by}'],
title: 'Evidence expiring soon: {ev.title}',
body:
'Evidence "{ev.title}" expires on {ev.expires_on}. Collect a fresh copy and resubmit.',
link: '/objects/compliance_evidence/{ev.id}',
body: 'Evidence "{ev.title}" expires on {ev.expires_on}. Collect a fresh copy and resubmit.',
actionUrl: '/objects/compliance_evidence/{ev.id}',
},
},
{ id: 'end', type: 'end', label: 'End' },
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -50,15 +50,13 @@ export const FailedControlEscalationFlow: Flow = {
},
{
id: 'notify_owner',
type: 'script',
type: 'notify',
label: 'Notify Control Owner',
config: {
actionType: 'notification',
recipients: ['{ctrl.owner}', 'role:compliance_admin'],
title: 'Failed control: {ctrl.code} {ctrl.title}',
body:
'Assessment "{asmt.title}" on {ctrl.code} ({ctrl.criticality}) FAILED. Remediation due {asmt.remediation_due}.',
link: '/objects/compliance_assessment/{asmt.id}',
body: 'Assessment "{asmt.title}" on {ctrl.code} ({ctrl.criticality}) FAILED. Remediation due {asmt.remediation_due}.',
actionUrl: '/objects/compliance_assessment/{asmt.id}',
},
},
{ id: 'end', type: 'end', label: 'End' },
Expand Down
2 changes: 0 additions & 2 deletions packages/content/objectstack.config.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,6 @@ import * as apps from './src/apps/index.js';
import { ContentTranslations } from './src/translations/index.js';
import { allFlows } from './src/flows/index.js';
import { allHooks } from './src/hooks/index.js';
import { allApprovals } from './src/approvals/index.js';
import { allSharingRules, RoleHierarchy } from './src/sharing/index.js';
import { ContentSeedData } from './src/data/index.js';

Expand All @@ -38,7 +37,6 @@ export default defineStack({
apps: Object.values(apps),
flows: allFlows,
hooks: allHooks,
approvals: allApprovals,
translations: [ContentTranslations],

sharingRules: allSharingRules,
Expand Down
24 changes: 12 additions & 12 deletions packages/content/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -15,20 +15,20 @@
"start": "objectstack start -p 4008",
"build": "objectstack build",
"typecheck": "tsc --noEmit",
"test": "objectstack test"
"test": "objectstack build"
},
"dependencies": {
"@objectstack/account": "^7.3.0",
"@objectstack/cli": "^7.3.0",
"@objectstack/driver-memory": "^7.3.0",
"@objectstack/driver-sql": "^7.3.0",
"@objectstack/driver-sqlite-wasm": "^7.3.0",
"@objectstack/metadata": "^7.3.0",
"@objectstack/objectql": "^7.3.0",
"@objectstack/runtime": "^7.3.0",
"@objectstack/service-analytics": "^7.3.0",
"@objectstack/service-automation": "^7.3.0",
"@objectstack/spec": "^7.3.0",
"@objectstack/account": "^7.4.1",
"@objectstack/cli": "^7.4.1",
"@objectstack/driver-memory": "^7.4.1",
"@objectstack/driver-sql": "^7.4.1",
"@objectstack/driver-sqlite-wasm": "^7.4.1",
"@objectstack/metadata": "^7.4.1",
"@objectstack/objectql": "^7.4.1",
"@objectstack/runtime": "^7.4.1",
"@objectstack/service-analytics": "^7.4.1",
"@objectstack/service-automation": "^7.4.1",
"@objectstack/spec": "^7.4.1",
"sql.js": "^1.14.1"
},
"optionalDependencies": {
Expand Down
6 changes: 0 additions & 6 deletions packages/content/src/approvals/index.ts

This file was deleted.

79 changes: 0 additions & 79 deletions packages/content/src/approvals/publish_approval.approval.ts

This file was deleted.

2 changes: 2 additions & 0 deletions packages/content/src/flows/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,14 @@

import { SignalToTopicPromotionFlow } from './signal_to_topic_promotion.flow';
import { CtaCreationDefaultFlow } from './cta_creation_default.flow';
import { PublishApprovalFlow } from './publish_approval.flow';
import { PublicationRollupFlow } from './publication_rollup.flow';
import { StampLifecycleTimestampsFlow } from './stamp_lifecycle_timestamps.flow';

export const allFlows = [
SignalToTopicPromotionFlow,
CtaCreationDefaultFlow,
PublishApprovalFlow,
PublicationRollupFlow,
StampLifecycleTimestampsFlow,
];
3 changes: 2 additions & 1 deletion packages/content/src/flows/publication_rollup.flow.ts
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,8 @@ export const PublicationRollupFlow: Flow = {
label: 'Start',
config: {
objectName: 'content_metric',
criteria: 'ISCHANGED(views) OR ISCHANGED(clicks) OR ISCHANGED(signups) OR ISCHANGED(revenue) OR ISNEW()',
criteria:
'ISCHANGED(views) OR ISCHANGED(clicks) OR ISCHANGED(signups) OR ISCHANGED(revenue) OR ISNEW()',
},
},
{
Expand Down
Loading
Loading