Rebuild against kamo-shared-library 63827887
Picks up the comp-provisioning fix. A comped order granted its plan and none of the add-ons it sold, because provisionCompSubscription never wrote active_addon_...
Do not mail a tenant its own domain until that domain is verified
A domain typed into the create form is a CLAIM, not a host. Ownership is proven by a DNS TXT record afterwards and a certificate is issued after that, so betwee...
Stop a failed welcome email from destroying the member
MemberCreationService documented steps 4-6 as best effort, and for the emails it was not true. sendVerificationEmail is @Transactional, so it joined the member-...
Enter a tenant organization as one of its members, from /network
A second door beside the same-org god-mode one. Gated on the new IMPERSONATE platform right via @RequirePlatformRight, where the existing door is gated on the s...
Open a workspace on its OWN domain, not the host the sign-in was served from
A member who signed in on login.kamocrm.com, picked a workspace from the chooser, and landed inside it — on internal.kamocrm.com, wearing the platform's hostnam...
Rebuild against kamo-shared-library HEAD
Ships the lead contact location fix, which lives in the shared library: LeadDTO now returns the lead's own country, subdivision and timezone, so the three Prima...
Hold withTermsUnchanged to carrying every field
The method rebuilds UpdateQuoteRequest positionally, so a field added to that record and forgotten here is dropped from every save by a member without EDIT_QUOT...
Stop dropping setupFee on save, and unbreak the build
withTermsUnchanged rebuilds UpdateQuoteRequest positionally for a member who may not rewrite the terms. setupFee was added to that record and not added here, so...
Rebuild against kamo-shared-library HEAD
Ships the quote document work, all of which lives in the shared library: - a one-off setup fee on a single-price quote (commerce_quotes.setup_fee, which is a...
A share link's email was dropped twice before it could be sent
"I created a link and got no email." Two independent silent drops, both of which return a swallowed false that the panel rendered as plain success. 1. kamo.ema...
Rebuild against kamo-shared-library HEAD
Ships the quote pricing fix: a unit price is a per-month rate, so a term multiplies it rather than the engine dividing down to it. An annual option quoted one m...
Rebuild against kamo-shared-library HEAD
Ships the quote total fixes: a committed term now totals the term rather than one period of it, and a multi-option quote is no longer headlined by whichever alt...
A member address signs you into its own org, not every org
A member who signs in with the org mailbox flagged Primary on their member settings was being offered every workspace their user account belongs to. The address...
Rebuild against kamo-shared-library HEAD
Ships the quote money fixes, which live entirely in the shared library and so reach production only when this service is rebuilt: - a quote's headline total no...
Enforce the platform's visibility, and let it be edited
GET/PUT /api/security/reports/catalog, both gated on MANAGE_REPORTS on the platform spine. The list comes from the REGISTRY, not the override table: an operator...
Run the reports that are due, and send them
One internal endpoint, X-Internal-Auth gated and constant-time compared, that DaemonService ticks. The cron stays in the daemon because it is replicas: 1 with s...
The lists a share dialog picks from, and a share target that fits every id
GET **************** returns the organization's people, departments and roles as picker options, in one call and in one shape. Built on the reporting option pro...
Run, export and schedule the Report Studio's reports
The service half of the framework: the catalogue, the run, the pickers, four exporters, saved views and schedules. Authorization is explicit on every path, bec...
Pin the status-label body an org sends to drop a label
The two shapes that used to fail: an empty list, which is what clearing the last remaining label sends and what the handler rejected as malformed, and an entry ...
Accept a blank status label as the removal it is
The PUT is the org's complete set of custom labels, so it has to be able to carry an emptied box. Two things stopped it: an empty list was rejected as a malform...
Rebuild against the shared library that persists the quote contact
The market writer landed one commit after this service was last built, and CI clones kamo-shared-library at image-build time — so the deployed jar still has the...
Honour a market's contact rule wherever a quote names somebody
The staff detail, the staff preview and the customer's own page now resolve the contact through one method, so they cannot disagree about who is printed on the ...
Page and search the org directory, and stop two row builders drifting
The networks endpoints answer with the whole set in one body. That is fine for a member of a dozen orgs and impossible for an operator on an estate meant to rea...
Rebuild to pick up BillingCycle.TRIENNIAL
No source change. SecurityService clones kamo-shared-library at image-build time, and the catalog it serves is about to carry TRIENNIAL price rows. @Enumerated ...
Put the report title in the message, and let it be corrected
A dispatch composed the operator's instruction and the bug description with the separator between them. The title was never in it, so the session opening the me...
The agent health preflight must fail in seconds, not twenty
health() inherited the client's 20-second default. It is a liveness check in front of every KamoDesktop launch, and when the dev machine ran out of memory on 20...
Bulk-create members and team members, one transaction per record
The two bulk-add screens need to create a spreadsheet of people in one submission and report on each of them individually. That could not be built on the existi...
Store the org's deposit account, and print it on quotes
`/api/security/receivables` is where Settings → Account → Receivables reads and writes. Two rights, not one: VIEW_RECEIVABLES reads the tab, MANAGE_RECEIVABLES ...
Carry the team member's department in the session
The browser tab is being retitled "{Org} - {role} Portal", and a team member's role is their department — the specific thing they identify with day to day ("Sal...
Stop refusing a domain because somebody else typed it first
Creating an organization 409'd on any existing row for the domain, which meant the first organization to enter "acme.com" locked out every other one — including...
Give the generated favicons the same revalidation requirement as every other theme asset
Replacing an org's simple logo updated every surface that reads img/logo.svg and left the browser tab on the old mark. Generation was never the problem: provisi...
Say in the class contract that the gate can fall open
The header promised "a blocked app's endpoints all 403" without qualification, which is now true only while the entitlement tables can be read. The exception is...
A transient database fault must not 500 the request
The lead Communications tab reported "We couldn't load this lead's communications" for org 1168485648209608710 on 2026-08-28. The endpoint returned 500 five tim...
Carry the per-member-type home-screen defaults
Read on POST/PUT /security-models and PUT /master-model, and emitted from /applied-model's settings so the shell can decide where a member lands on "/". A sepa...
Send To AI straight off the report form
A holder of MANAGE_SYSTEM_BUGS gets a SEND TO AI switch on the Report Bug window, and submitting with it on hands the report to a session without the triage dia...
Require an open god-mode window, not eligibility alone, for CONFIGURE_SYSTEM
hasRight was granting the bypass on the raw GD session flag, which SessionPlatformFacts's own javadoc names as the exact anti-pattern it exists to prevent: GD i...
Add progress service and endpoints behind the Getting Started wizard
Org-scoped GET/PUT/DELETE under /api/security/org-setup-wizard track which of the nine Getting Started steps an organization has completed. A read never creates...
Put a real time budget on resend-verification
The endpoint had no limit of any kind. The *** the register screen demanded before enabling its resend button was never read here — the request body is three fi...
Seed the master-note widgets from VIEW_NOTES
The two master-note panes shipped with no right at all — "My Master Note" and "Our Master Note" were on every member's launchpad unconditionally — and this is t...
Make seeded and uploaded branding revalidate, so an org stops being served the base theme it was seeded with
A new organization is seeded with the base theme — the platform's own logo and backgrounds copied to the new org's keys — and those keys never change when the o...
Let the caller choose a fixed KamoDesktop resolution
The remote desktop was never locked to a resolution — it tracks the browser window, and always has. guacd honours the client's size and xorgxrdp resizes the X s...
The relay to InvoicingService, and the right that gates it
Task 8. SecurityService is the authorization boundary; InvoicingService is ClusterIP with no ingress, so this relay is the only way in. InvoicingServiceClient ...
Tell the reporter when Send To AI moves their report
MediaService now emails a reporter whenever their bug or enhancement changes status, but a dispatch applies a status of its own — usually In Progress — through ...
Announce the queue change when a report is dispatched to AI
A dispatch is the only thing that takes a report out of NEW from OUTSIDE MediaService, so without this it was the one transition the console's badge learned abo...
A video on a report never reaches an AI dispatch
file and cannot watch one. The desktop agent already magic-byte-checks every attachment, but it refuses the DISPATCH rather than the one file — so a single vide...
The Traefik per-IP limit will 429 a QHIN invisibly
Comment only, in the file somebody opens when a partner complains. Traefik rate-limits per source IP across the whole api.* host, and a QHIN sits behind a sing...
Pin the exact JSON the clinical client parses
Every field in these bodies is read by name in app/lib/patients/ehrApi.ts and nothing was checking the server still emits them. The service tests pin that the e...
POST /service-jobs, gated on MANAGE_SERVICE_WORK
The create verb the work-order surface never had. app/commerce/service/new is a seventeen-line placeholder because there was nothing to call. Gated on MANAGE_S...
Rebuild to seed the four order and pricing rights
An empty commit built out of tree from origin's own tree. RoleRightsSyncService seeds org_role_rights at boot, so a right shipped without a SecurityService rebu...
Gate the order and pricing surfaces on a right
Thirty-nine endpoints were protected only by "are you signed in". Every order handler on POSController and every pricing and tax handler on CommerceMarketContro...
Like what you see shipping?
Every one of these updates lands in your workspace automatically. Start free and watch it grow week after week.