Count the files a document keeps only as old versions
A category that keeps versions holds every earlier file of a document in img_versions, each on its own content-addressed file. The storage meter, the quota and ...
An organization's own domain is named in a link only once it is live
OrgLinkHosts is the one rule for the host a link to an organization may name: its own root domain once it is active, ownership-verified and SSL-confirmed ******...
Rank only members whose security type includes achievements
The leaderboard grouped every member holding an achievement row, so a member whose role denies VIEW_ACHIEVEMENTS β who cannot open the page, the trophy or the w...
An app id an older build cannot name must not fail every feature read
ServiceType ships inside each service's jar while ORG_FEATURES is shared, so a newly added app is ALWAYS in the database before the older readers have been rebu...
Cover the three shared reads a catalog bump still reached users through
Same defect as the sign-in fix, found by reading the fleet's logs rather than one report: eight hours of pod logs across email, media, docs, daemon and security...
Retry the two rights reads that stand between a password and a session
MemberRightsAppliedService carried @RetryOnDbConflict on its WRITE entry points only. The class therefore read as covered while the two methods the authenticate...
The update DTO needs the first-time-buyer field too
68ce0e0f added `isFirstTimeBuyer` to the CREATE request and wired both call sites in LeadService β but the second one reads UpdateLeadRequest's own nested Mortg...
Put back the CRLF a Python edit stripped from two files
Both files are CRLF in this repo, and rewriting them through Python's text mode converted every line β turning a fifteen-line addition into a 771-line diff in 6...
Bring the organization inside the retried read instead of leaving it to fire later
Member.organization is LAZY, so findById left a proxy behind and the real SELECT happened whenever something first dereferenced it. Under open-in-view that is t...
Share the delivery consumer, so a second pod is not refused
Caught in production the moment services went to two replicas on 2026-09-04. Every pod carrying this class logged, once, at boot: [Webhook] Failed to subscri...
System_bug.published needs a column DEFAULT, or it is never created
The field was declared `@Column(nullable = false)` with no columnDefinition, so ddl-auto emitted `ADD COLUMN published boolean not null` β which Postgres REFUSE...
An empty platform registration is not "connect with Kamo's app"
isPlatformEnabled now also requires a client id, matching what OrgOAuthClientController reports as platformEnabled. Without that the meetings screen and the bri...
Comping an account now drops its cached entitlements
SecurityService answers /api/security/entitlements/me out of Redis with a 15-minute TTL, invalidated by messages on kamo.entitlements.invalidate. Every self-ser...
Editing a draft order's seats or cycle now reprices it
updateDraftOrder set seatCount and billingCycle and saved. Both are price drivers, and neither the order's money fields nor its line items were touched, so the ...
A comped order now grants the add-ons it sold
Comping an account granted the plan and nothing else. provisionCompSubscription copied plan, seats, cycle, source and status onto the AccountSubscription and ne...
Bind content_json as JSON, or every insert fails
REPORTED: "Failed to create sales script". The server said exactly why: column "content_json" is of type jsonb but expression is of type character varying ...
An archived market's scripts leave the Interaction Center
findMarketIdsWithActiveScripts asked only whether the SCRIPT was active, so a market the organization had retired still appeared as a sub-tab for as long as any...
Flush the link, so a refused write reaches the catch that reports it
link() is @Transactional(REQUIRES_NEW), so its transaction commits in the proxy after the method body returns. A plain save() of an entity whose id is generated...
Return the contact's country, state and time zone
LeadDTO carried neither Lead.country, Lead.subdivision nor Lead.timezone, so the three fields were write-only: UpdateLeadRequest accepted them and LeadService w...
An address is several lines, so send it as several lines
Splitting the suite out of addressLine was not enough β it left the street and the city sharing a line with the unit printed beneath them, which is worse than t...
Restore the timestamp that every lead association depends on
A method was inserted between @CreationTimestamp and the dateCreated field it annotates, so the annotation bound to subject() instead. These entities are read b...
A unit price is a MONTHLY rate, so the term multiplies it
The engine treated an option's line-item sum as the price for the whole billing period and divided down to reach a monthly figure. It is the other way round. P...
A three-year deal totals three years, not one month of it
Two faults, both showing a monthly figure where the term's value belonged. 1. The headline took periodTotal + setup. On a MONTHLY option committed to 36 mon...
The one-time setup fee belongs in the quote's total
A setup fee typed on an option reached exactly one figure β QuoteOptionTotals put it in contractTotal β and applyOptionHeadlineTotals then built the quote's hea...
ReportDefinition never shipped the narrower rights its resolver reads
ReportScopeResolver, its test and this class's own javadoc all name alsoGrantedBy, and ReportSecurityScope has had SELF/TEAM/ORGANIZATION since the framework la...
Let an org put a custom status label back to blank
A status label had no way to be removed. The settings screen saved through an upsert-only bulk write, so the only thing a request could say was "this status is ...
A join/leave row has to carry the name of who it is about
The id alone cannot be resolved in the one case these rows exist for. A "removed" or "left" line names somebody who is, by then, no longer in the session, so th...
Declare removedByMemberId, or the relay drops it in silence
The NATS payload for MEMBER_REMOVED carries who did the removing, but the NATSβSTOMP relay projects every frame through ChatMessageDto β so a field this class d...
Filter every durable consumer to its own subject
A durable created through NatsMessageService.subscribe carried no filter subject, so it received the WHOLE stream regardless of the subject it was asked for. Th...
A vendor id leaves as a string, for every row
`commerce_vendors.uid` is `INT8 DEFAULT unique_rowid()` -- about 19 digits, where `Number.MAX_SAFE_INTEGER` has sixteen. A numeric id of that size is an IEEE-75...
Actually call the fulfillment policy
SW3 implemented FulfillmentPolicy as the first member of an interface that had none, and nothing ever called it β a grep across kamo-shared-library and Security...
The document upload publishes its row only once the bytes land
The buffered uploadDocument was the one store that wrote its ImgDat with isMissing=false BEFORE sending anything, and merely re-set it to false after a successf...
A failed upload must not become a dedup match
A member sent an 11 MB .wav to a chat, got "Cannot invoke ObjectWriteResponse.etag() because response is null", sent it again, and the second one delivered inst...
Let the database decide whether a reaction is already there
The unique constraint on (message, member, emoji) was doing nothing useful. A read-then-save loses the race with the member's own second click, and catching the...
An unread count names a sender only when a single member is the answer
senderId is what pins an unread badge to a person β their member-directory row, their hex head β so it has to mean "these messages are from them". It was set fo...
Editing top-level lines no longer deletes every option's lines
Quote.lineItems is orphanRemoval=true and option rows set both quote and option β which is why QuoteMapper filters on getOption() == null twice. A bare clear() ...
An option quote keeps the tax and shipping staff entered
recalculate zeroed taxTotal and shippingTotal whenever a quote had options. Both were still stored on the row and still rendered by QuoteMapper, so a staff memb...
Terminal guards on cancel and revise, and stop swallowing bad input
cancel() and revise() had no isTerminal() guard, so an ACCEPTED quote could be flipped to CANCELLED or REVISED while acceptedAt and acceptedByName survived β a ...
Stop dropping the market and the customer account
CreateQuoteRequest has always declared marketUid and accountUid and QuoteService.create has never read either, so Quote.market and Quote.customerAccount were NU...
Pin ServiceJob's join columns to INT8
Exporting the table's DDL showed org_id, engagement_id and customer_uid each emitted as INT8 DEFAULT unique_rowid() β inherited from the referenced key. Three f...
Stop discarding status changes and answering 200
updateWorkOrder parsed the requested status inside catch (Exception ignored), saved the entity unchanged, and returned 200 with a DTO showing the old value. The...
Delete findConflictingEvents, which never returned a row
Four independent defects, any one of which emptied the result set: it filtered e.user.id while both callers pass a member id and the two columns never coincide;...
Carry the assignee into the account rollup, over a LEFT join
Reading a lead's communications is gated on who it is assigned to. A rollup that returned uids alone could not apply that gate, so the account timeline built on...
Make the retail webhook signature check fail closed and compare in constant time
validateSignature used to return true three ways without verifying anything: a null secret short-circuited, six of eleven provider types fell through default ->...
Stop the bug list 500ing on every unfiltered load
PostgreSQL cannot infer a type for a null parameter inside a string expression: LOWER(CONCAT('%', :search, '%')) with a null :search guessed bytea, and the list...
Add the AiDispatchRequest the pushed code already imports
SecurityService's SystemBugAiDispatchController and SystemBugAiDispatchService are on main and import **************** but the record itself was never committed...
The five pre-existing verticals must ship available
Shipping all six children PLANNING was wrong for five of them. RETAIL, RENTAL, SERVICE, SUBSCRIPTION and PROCUREMENT are not new functionality β they are what C...
Do not bill an org twice for a version that owns no bytes
The org storage total is SUM(fileSize) over Img rows, and a derived version points at its original's ImgDat while copying its fileSize β so every modified versi...
Put the timecard widget under the HR group, like every other widget
TIMECARD_TODAY_WIDGET now hangs off MANAGE_TIMECARDS instead of being a root, so all five widgets have the identical shape the calendar ones set: a parent data ...
Restore the CRLF line endings in CalendarEventAttendeeRepository
A scripted edit rewrote the file through a text API, normalising all 62 CRLF line endings to LF and turning a 15-line addition into a 139-line diff. The content...
Like what you see shipping?
Every one of these updates lands in your workspace automatically. Start free and watch it grow week after week.