Skip to main content

Backend API Reference

Base URL: /api/v1


Technical Specifications & Models

Architectural Diagrams


Table of Contents


Models

PlatformUser

File: internal/repository/platform_users.go

FieldTypeJSON
UserIDuuid.UUIDuser_id
Emailstringemail
PasswordHashstring- (hidden)
FirstNamestringfirst_name
LastNamestringlast_name
Rolestringrole
Activeboolactive
LastLogin*time.Timelast_login
CreatedAttime.Timecreated_at
UpdatedAttime.Timeupdated_at

Organization

An Organization is a grouping of Stores (see Store) controlled by one Owner.

SSO UPSELL - Potential future feature

File: internal/repository/organizations.go

Attributes:

FieldTypeJSONDescription
OrgIDuuid.UUIDorg_idUnique identifier
NamestringnameFriendly name
EINstringeinEmployer Identification Number
SlugstringslugURL-friendly identifier (e.g., peakpos.co/pinpoint-payments)
ActiveboolactiveWhether organization is active
CreatedAttime.Timecreated_atDatabase creation timestamp
UpdatedAttime.Timeupdated_atDatabase update timestamp
HQLocationstringhq_locationHeadquarters location (derives timezone)
TimeOffsetinttime_offsetTime zone offset

Dependents:

  • Suppliers
  • Stores (see Store)
  • Product Categories (user-definable)
  • Products (see Products) - modifiable by Stores and Organization
  • Users (see User) - via Master User (all groups) and OrgMembership object

Store

A Store is a Place/Point of Sale.

File: internal/repository/stores.go

Attributes:

FieldTypeJSONDescription
StoreIDuuid.UUIDstore_idUnique identifier
OrgIDuuid.UUIDorg_idParent organization
NamestringnameStore name
AddressLine1*stringaddress_line1Street address
AddressLine2*stringaddress_line2Suite/unit number
City*stringcityCity
State*stringstateState
ZipCode*stringzip_codeZIP/Postal code
Phone*stringphoneContact phone
CurrencystringcurrencyCurrency code
TimezonestringtimezoneStore timezone
OpeningTime*stringopening_timeOpening time (7-day schedule)
ClosingTime*stringclosing_timeClosing time (7-day schedule)
RCN*stringrcnRegistration/compliance number
ActiveboolactiveWhether store is active
OnboardingCompletedboolonboarding_completedOnboarding status
CreatedAttime.Timecreated_atDatabase creation timestamp
UpdatedAttime.Timeupdated_atDatabase update timestamp

Dependents:

  • Terminals
  • Products (see Products)
  • Inventory
  • Shifts
  • Users (see User)
  • ComplianceChecks

User

Any person who accesses this platform.

File: internal/repository/users.go

Attributes:

FieldTypeJSONDescription
UserIDuuid.UUIDuser_idUnique identifier
EmailstringemailUser email
PasswordHashstring- (hidden)Hashed password
FirstNamestringfirst_nameFirst name
LastNamestringlast_nameLast name
PIN*string- (hidden)PIN for quick login
ActiveboolactiveWhether user is active
LastLogin*time.Timelast_loginLast login timestamp
CreatedAttime.Timecreated_atDatabase creation timestamp
UpdatedAttime.Timeupdated_atDatabase update timestamp
Roles[]RolerolesUser roles
RoleIDuuid.UUIDrole_idPrimary role identifier
GroupIDs[]uuid.UUIDgroup_idsList of group memberships
TaxInfoobjecttax_infoTax information (NO SSN!)
AccountingID*stringaccounting_idE.g., QuickBooks EmployeeUUID
PayrollID*stringpayroll_idE.g., QuickBooks EmployeeUUID

Dependent to:

  • Organizations
  • Stores
  • Shifts

Tech Support User:

A special type of user created via any interaction with a user who belongs to an organization. This includes generic employees. Tech support users receive privileges equivalent to the user who requested tech support.

  • Time-limited role that expires in one hour

OrgMembership

File: internal/repository/org_memberships.go

FieldTypeJSON
MembershipIDuuid.UUIDmembership_id
OrgIDuuid.UUIDorg_id
UserIDuuid.UUIDuser_id
Rolestringrole
CreatedAttime.Timecreated_at

OrgMembershipWithUser extends the above with:

FieldTypeJSON
Emailstringemail
FirstNamestringfirst_name
LastNamestringlast_name
Activeboolactive

StoreMembership

File: internal/repository/store_memberships.go

FieldTypeJSON
MembershipIDuuid.UUIDmembership_id
StoreIDuuid.UUIDstore_id
UserIDuuid.UUIDuser_id
Rolestringrole
Clearancesintclearances
CreatedAttime.Timecreated_at

StoreMembershipWithUser extends the above with:

FieldTypeJSON
Emailstringemail
FirstNamestringfirst_name
LastNamestringlast_name
Activeboolactive

Invite

File: internal/repository/invites.go

FieldTypeJSON
InviteIDuuid.UUIDinvite_id
OrgIDuuid.UUIDorg_id
StoreID*uuid.UUIDstore_id
Emailstringemail
FirstName*stringfirst_name
LastName*stringlast_name
OrgRole*stringorg_role
StoreRole*stringstore_role
Tokenstringtoken
Statusstringstatus
ExpiresAttime.Timeexpires_at
AcceptedAt*time.Timeaccepted_at
CreatedBy*uuid.UUIDcreated_by
CreatedAttime.Timecreated_at

Product

A product sold in an organization.

File: internal/repository/products.go

Attributes:

FieldTypeJSONDescription
ProductIDuuid.UUIDproduct_idUnique identifier
StoreIDuuid.UUIDstore_idStore(s) where product is sold
BarcodestringbarcodeBarcode/SKU
NamestringnameProduct name
Description*stringdescriptionProduct description
SupplierID*uuid.UUIDsupplier_idSupplier reference
Pricedecimal.DecimalpriceSelling price
Costdecimal.DecimalcostCost price
RequiresSerialboolrequires_serialWhether product requires serial number tracking
Over18boolover_18Requires 18+ age verification
Over21boolover_21Requires 21+ age verification
TaxRatedecimal.Decimaltax_rateTax rate for product
StockintstockTotal stock (tied with sum(inventory, product, all stores))
ProductTypestringproduct_typeType/category of product
ActiveboolactiveWhether product is active
CreatedAttime.Timecreated_atDatabase creation timestamp
UpdatedAttime.Timeupdated_atDatabase update timestamp

Dependents:

  • Inventory
  • SerialNumber
  • ProductCategory
  • Supplier

ProductCategory

Categories for products.

File: internal/repository/product_categories.go

Attributes:

FieldTypeJSONDescription
CategoryIDuuid.UUIDcategory_idUnique identifier
OrgIDuuid.UUIDorg_idParent organization
IsChildboolis_childWhether this is a child category
ParentID*uuid.UUIDparent_idParent category ID (for nested categories)
NamestringnameCategory name
SlugstringslugURL-friendly identifier
Depthint16depthNesting depth level
SortOrderintsort_orderDisplay order
ActiveboolactiveWhether category is active
CreatedAttime.Timecreated_atDatabase creation timestamp
UpdatedAttime.Timeupdated_atDatabase update timestamp

Supplier

A company that makes or distributes a product to the store.

File: internal/repository/suppliers.go

Attributes:

FieldTypeJSONDescription
SupplierIDuuid.UUIDsupplier_idUnique identifier
OrgIDuuid.UUIDorg_idParent organization
NamestringnameSupplier name
ContactEmail*stringcontact_emailContact email address
ContactPhone*stringcontact_phoneContact phone number
ActiveboolactiveWhether supplier is active
CreatedAttime.Timecreated_atDatabase creation timestamp
UpdatedAttime.Timeupdated_atDatabase update timestamp

ProductSupplier (junction):

FieldTypeJSONDescription
ProductIDuuid.UUIDproduct_idProduct reference
SupplierIDuuid.UUIDsupplier_idSupplier reference
SupplierSKU*stringsupplier_skuSupplier's SKU for this product
Cost*decimal.DecimalcostCost from this supplier
IsPreferredboolis_preferredWhether this is the preferred supplier

Customer

File: internal/repository/customers.go

Attributes:

FieldTypeJSONDescription
CustomerIDuuid.UUIDcustomer_idUnique identifier
OrgIDuuid.UUIDorg_idParent organization
DOB*time.TimedobDate of birth
FirstName*stringfirst_nameFirst name
LastName*stringlast_nameLast name
Email*stringemailEmail address
Phone*stringphonePhone number
PointsintpointsLoyalty points
CreatedAttime.Timecreated_atDatabase creation timestamp
UpdatedAttime.Timeupdated_atDatabase update timestamp

InventoryEntry

Also known as StoreInventoryItem.

File: internal/repository/inventory.go

Attributes:

FieldTypeJSONDescription
InventoryIDuuid.UUIDinventory_idUnique identifier (StoreInventoryItemID)
StoreIDuuid.UUIDstore_idStore reference
OrgIDuuid.UUIDorg_idOrganization reference
ProductIDuuid.UUIDproduct_idProduct reference
QuantityintquantityCurrent quantity
Pricedecimal.DecimalpricePrice at this store
ChangeTypestringchange_typeType of inventory change
ReferenceID*uuid.UUIDreference_idReference to related entity
UserID*uuid.UUIDuser_idUser who made the change
SourceStoreID*uuid.UUIDsource_store_idSource store for transfers
DestStoreID*uuid.UUIDdestination_store_idDestination store for transfers
Notes*stringnotesAdditional notes
CreatedAttime.Timecreated_atDatabase creation timestamp

Dependents:

  • Inventory Ledger Update

Depends on:

  • Store
  • Product

InventoryLevel / LedgerEntry

Also known as InventoryLedgerUpdate.

File: internal/repository/inventory_ledger.go

InventoryLevel:

FieldTypeJSONDescription
StoreIDuuid.UUIDstore_idStore reference
ProductIDuuid.UUIDproduct_idProduct reference
QuantityOnHandintquantity_on_handCurrent quantity on hand
ReorderPoint*intreorder_pointThreshold for reorder alert
ReorderQty*intreorder_qtySuggested reorder quantity
LastCountedAt*time.Timelast_counted_atLast physical count timestamp
UpdatedAttime.Timeupdated_atDatabase update timestamp

LedgerEntry (InventoryLedgerUpdate):

FieldTypeJSONDescription
LedgerIDuuid.UUIDledger_idUnique identifier (ReferenceID)
StoreIDuuid.UUIDstore_idStore reference
OrgIDuuid.UUIDorg_idOrganization reference
ProductIDuuid.UUIDproduct_idProduct reference
StoreInventoryItemIDuuid.UUIDstore_inventory_item_idFrom inventory item
QuantityChangeintquantity_changeQuantity delta
ChangeTypestringchange_typeType of change
ReferenceType*stringreference_typeType of referenced entity
ReferenceID*uuid.UUIDreference_idID of this update
UserID*uuid.UUIDuser_idUser that made change
Notes*stringnotesAdditional notes
CreatedAttime.Timecreated_atDatabase creation timestamp

Depends on:

  • StoreInventoryItem

SerialNumber

File: internal/repository/serial_numbers.go

Attributes:

FieldTypeJSONDescription
SerialIDuuid.UUIDserial_idUnique identifier
OrgIDuuid.UUIDorg_idOrganization reference
StoreIDuuid.UUIDstore_idStore reference
ProductIDuuid.UUIDproduct_idProduct reference
SerialNumberstringserial_numberThe serial number string
StatusstringstatusCurrent status (available, sold, returned)
ReceivedAttime.Timereceived_atWhen serial was received
SoldAt*time.Timesold_atWhen serial was sold
TransactionID*uuid.UUIDtransaction_idAssociated transaction
UserID*uuid.UUIDuser_idUser who sold to / received from
Notes*stringnotesAdditional notes
RequiredForms*stringrequired_formsAny required forms (point to S3)

Transaction

File: internal/repository/transactions.go

Attributes:

FieldTypeJSONDescription
TransactionIDuuid.UUIDtransaction_idUnique identifier
TransactionRefinttransaction_refNon-unique int for Dejavoo
StoreIDuuid.UUIDstore_idStore reference
OrgIDuuid.UUIDorg_idOrganization reference
ProductIDs[]uuid.UUIDproduct_idsList of product IDs
UserIDuuid.UUIDuser_idCashier/employee
CustomerID*uuid.UUIDcustomer_idCustomer (optional)
TerminalID*uuid.UUIDterminal_idTerminal used
Datetimetime.TimedatetimeTransaction timestamp
Subtotaldecimal.DecimalsubtotalSubtotal before tax/discount
TaxApplieddecimal.Decimaltax_appliedTotal taxes
DiscountTotaldecimal.Decimaldiscount_totalTotal discounts
TotalSpentdecimal.Decimaltotal_spentFinal total
AmountPaidWithCashdecimal.Decimalamount_paid_cashCash amount
AmountPaidWithCarddecimal.Decimalamount_paid_cardCard amount
PaymentMethodstringpayment_methodPayment method (Cash, card, etc) (Enum)
StatusstringstatusTransaction status
CreatedAttime.Timecreated_atDatabase creation timestamp
UpdatedAttime.Timeupdated_atDatabase update timestamp

Depends on:

  • Store
  • Organization
  • Customer (Optional)
  • InventoryLedgerUpdate(s) [list of updates]
  • Return (Optional)
  • Discount(s) (Optional)

Dependencies:

  • DejavooCardAuthorization (Optional)

TransactionItem:

FieldTypeJSONDescription
ItemIDuuid.UUIDitem_idUnique identifier
TransactionIDuuid.UUIDtransaction_idParent transaction
ProductIDuuid.UUIDproduct_idProduct reference
QuantityintquantityQuantity purchased
UnitPricedecimal.Decimalunit_pricePrice per unit
DiscountApplieddecimal.Decimaldiscount_appliedDiscount on this item
TaxApplieddecimal.Decimaltax_appliedTax on this item
LineTotaldecimal.Decimalline_totalTotal for this line

TransactionPayment:

FieldTypeJSONDescription
PaymentIDuuid.UUIDpayment_idUnique identifier
TransactionIDuuid.UUIDtransaction_idParent transaction
PaymentMethodstringpayment_methodMethod (cash, card, etc)
Amountdecimal.DecimalamountAmount paid
ReferenceNum*stringreference_numExternal reference number
ProcessedAttime.Timeprocessed_atWhen payment was processed

TransactionDetail extends Transaction with:

FieldTypeJSONDescription
UserNamestringuser_nameEmployee name
CustomerName*stringcustomer_nameCustomer name
Items[]TransactionItemitemsTransaction items
Payments[]TransactionPaymentpaymentsPayment records

Receipts

Receipts are generated from Transactions for customer-facing documentation.

Note: Implementation details TBD - likely generated from Transaction data.


DejavooCardAuthorization

Status: TBD

Card authorization records for Dejavoo payment processing.

Attributes:

FieldTypeJSONDescription
AuthorizationIDuuid.UUIDauthorization_idUnique identifier
TransactionIDuuid.UUIDtransaction_idParent transaction
.........TBD

Dependencies: N/A

Depends on:

  • Transaction

Batch

Status: TBD

Batch processing for card authorizations.

Attributes:

FieldTypeJSONDescription
BatchIDuuid.UUIDbatch_idUnique identifier
StoreIDuuid.UUIDstore_idStore reference
BatchNumberstringbatch_numberBatch number
AuthorizationIDs[]uuid.UUIDauthorization_idsList of authorization IDs
BatchStatusstringbatch_statusStatus (enum)

Dependencies: N/A

Depends on:

  • DejavooCardAuthorization

Return

File: internal/repository/returns.go

FieldTypeJSON
ReturnIDuuid.UUIDreturn_id
StoreIDuuid.UUIDstore_id
UserIDuuid.UUIDuser_id
CustomerID*uuid.UUIDcustomer_id
ProductIDuuid.UUIDproduct_id
TransactionID*uuid.UUIDtransaction_id
Quantityintquantity
RefundAmountdecimal.Decimalrefund_amount
DateReturnedtime.Timedate_returned
Reasonstringreason
ReasonNotes*stringreason_notes
Restockedboolrestocked
CreatedAttime.Timecreated_at

ReturnWithDetails extends the above with:

FieldTypeJSON
UserNamestringuser_name
ProductNamestringproduct_name
CustomerName*stringcustomer_name

Discount

File: internal/repository/discounts.go

Attributes:

FieldTypeJSONDescription
DiscountIDuuid.UUIDdiscount_idUnique identifier
OrgIDuuid.UUIDorg_idOrganization reference
StoreIDuuid.UUIDstore_idStore reference
ProductID*uuid.UUIDproduct_idProduct reference (optional)
QtyintqtyQuantity threshold
NamestringnameDiscount name
Description*stringdescriptionDiscount description
TypestringtypeDiscount type (enum)
Discountdecimal.DecimaldiscountDiscount amount (float)
StartDatetime.Timestart_dateStart date
EndDatetime.Timeend_dateEnd date
ProductType*stringproduct_typeProduct type filter
DiscountTypestringdiscount_typeType (percent/fixed)
Amountdecimal.DecimalamountAmount value
MinPurchase*decimal.Decimalmin_purchaseMinimum purchase required
MaxDiscount*decimal.Decimalmax_discountMaximum discount cap
ActiveboolactiveWhether discount is active
CreatedAttime.Timecreated_atDatabase creation timestamp
UpdatedAttime.Timeupdated_atDatabase update timestamp

Dependencies:

  • Transaction

Depends On:

  • Organization
  • Store
  • Product

Promotion

File: internal/repository/promotions.go

FieldTypeJSON
PromotionIDuuid.UUIDpromotion_id
OrgIDuuid.UUIDorg_id
Namestringname
Description*stringdescription
PromotionTypestringpromotion_type
BuyQuantityintbuy_quantity
GetQuantityintget_quantity
DiscountValue*decimal.Decimaldiscount_value
AppliesToAllStoresboolapplies_to_all_stores
StartDatetime.Timestart_date
EndDatetime.Timeend_date
Activeboolactive
MaxUsesPerTransaction*intmax_uses_per_transaction
CreatedAttime.Timecreated_at
UpdatedAttime.Timeupdated_at
ProductIDs[]uuid.UUIDproduct_ids
StoreIDs[]uuid.UUIDstore_ids

ComplianceCheck

File: internal/repository/compliance.go

FieldTypeJSON
CheckIDuuid.UUIDcheck_id
OrgIDuuid.UUIDorg_id
StoreIDuuid.UUIDstore_id
TransactionID*uuid.UUIDtransaction_id
ProductIDuuid.UUIDproduct_id
UserIDuuid.UUIDuser_id
CheckTypestringcheck_type
IDType*stringid_type
IDDob*time.Timeid_dob
IDExpiry*time.Timeid_expiry
VerifiedAge*intverified_age
RequiredAgeintrequired_age
Resultstringresult
OverrideReason*stringoverride_reason
OverrideBy*uuid.UUIDoverride_by
CreatedAttime.Timecreated_at

ComplianceSummary:

FieldTypeJSON
TotalChecksinttotal_checks
Passesintpasses
Failsintfails
Overridesintoverrides

Notification

File: internal/repository/notifications.go

FieldTypeJSON
NotificationIDuuid.UUIDnotification_id
OrgIDuuid.UUIDorg_id
StoreID*uuid.UUIDstore_id
Typestringtype
Titlestringtitle
Messagestringmessage
Metadatajson.RawMessagemetadata
Readboolread
CreatedAttime.Timecreated_at

StockTransfer

File: internal/repository/stock_transfers.go

FieldTypeJSON
TransferIDuuid.UUIDtransfer_id
OrgIDuuid.UUIDorg_id
FromStoreIDuuid.UUIDfrom_store_id
ToStoreIDuuid.UUIDto_store_id
Statusstringstatus
InitiatedByuuid.UUIDinitiated_by
ReceivedBy*uuid.UUIDreceived_by
Notes*stringnotes
CreatedAttime.Timecreated_at
CompletedAt*time.Timecompleted_at
Items[]StockTransferItemitems

StockTransferItem:

FieldTypeJSON
IDuuid.UUIDid
TransferIDuuid.UUIDtransfer_id
ProductIDuuid.UUIDproduct_id
Quantityintquantity
ReceivedQty*intreceived_qty

TaxConfig

File: internal/repository/tax_configurations.go

FieldTypeJSON
TaxConfigIDuuid.UUIDtax_config_id
StoreIDuuid.UUIDstore_id
Label*stringlabel
JurisdictionTypestringjurisdiction_type
JurisdictionCode*stringjurisdiction_code
JurisdictionName*stringjurisdiction_name
RateTypestringrate_type
RateBps*intrate_bps
RateAmountMinor*int64rate_amount_minor
TaxBasisstringtax_basis
AppliesToCategory*uuid.UUIDapplies_to_category
Priorityintpriority
EffectiveFromstringeffective_from
EffectiveTo*stringeffective_to
Activeboolactive
CreatedAttime.Timecreated_at
UpdatedAttime.Timeupdated_at

Tax calculation rejects malformed jurisdiction_type or rate_type values instead of silently zero-rating them.


Tax Reports

Notes: tax report endpoints require explicit from and to query parameters; the API no longer invents a rolling default range.

MethodPathNotes
GET/stores/:store_id/tax-reportsRequires from and to
GET/stores/:store_id/tax-reports/summaryRequires from and to

Terminal

File: internal/repository/terminals.go

FieldTypeJSON
TerminalIDuuid.UUIDterminal_id
StoreIDuuid.UUIDstore_id
TerminalNamestringterminal_name
TerminalSecretstringterminal_secret
IsActiveboolis_active
LastSeen*time.Timelast_seen
CreatedAttime.Timecreated_at

Shifts

File: internal/repository/shifts.go

ShiftPreference:

FieldTypeJSON
PreferenceIDuuid.UUIDpreference_id
StoreIDuuid.UUIDstore_id
UserIDuuid.UUIDuser_id
DayOfWeekintday_of_week
StartTimestringstart_time
EndTimestringend_time
Priorityintpriority
CreatedAttime.Timecreated_at
UpdatedAttime.Timeupdated_at

ShiftAssigned:

FieldTypeJSON
AssignedIDuuid.UUIDassigned_id
StoreIDuuid.UUIDstore_id
UserIDuuid.UUIDuser_id
AssignedByuuid.UUIDassigned_by
ShiftDatetime.Timeshift_date
StartTimestringstart_time
EndTimestringend_time
Notes*stringnotes
CreatedAttime.Timecreated_at
UpdatedAttime.Timeupdated_at

ShiftActual:

FieldTypeJSON
ActualIDuuid.UUIDactual_id
StoreIDuuid.UUIDstore_id
UserIDuuid.UUIDuser_id
AssignedID*uuid.UUIDassigned_id
ShiftDatetime.Timeshift_date
ClockIn*time.Timeclock_in
ClockOut*time.Timeclock_out
BreakMinutesintbreak_minutes
NoShowboolno_show
CreatedAttime.Timecreated_at
UpdatedAttime.Timeupdated_at

ShiftRequest:

FieldTypeJSON
RequestIDuuid.UUIDrequest_id
StoreIDuuid.UUIDstore_id
UserIDuuid.UUIDuser_id
RequestedDatetime.Timerequested_date
StartTimestringstart_time
EndTimestringend_time
Statusstringstatus
ReviewedBy*uuid.UUIDreviewed_by
ReviewedAt*time.Timereviewed_at
Notes*stringnotes
CreatedAttime.Timecreated_at

ActivityLog

File: internal/repository/activity_log.go

FieldTypeJSON
LogIDuuid.UUIDlog_id
ActorTypestringactor_type
ActorIDuuid.UUIDactor_id
OrgID*uuid.UUIDorg_id
StoreID*uuid.UUIDstore_id
Actionstringaction
EntityType*stringentity_type
EntityID*uuid.UUIDentity_id
Detailsmap[string]interface{}details
IPAddress*stringip_address
CreatedAttime.Timecreated_at

Standard API Response Envelope

All responses use:

{
"success": true,
"data": { ... },
"error": { "code": "...", "message": "..." },
"meta": { "page": 1, "limit": 20, "total": 100, "total_pages": 5 }
}

Specifications

IAM

Individual Access Management specification for the platform.

Group

Definition: Non-user defined groups are an arbitrary grouping of services (API endpoints, microservices, etc.)

Permissions (AWS-style)

  • Permissions are assignable to a Group
  • Permissions should be the maximal grouping of API endpoints and/or microservices relevant to that Group

Roles

  • Roles are a user-defined selection of Groups that give access to a particular service
  • Roles are defined at an Organization level

Users

Users have the following IAM-related attributes:

  • REQUIRES a Role
  • Have a list of Role IDs
  • Have UUIDs that correspond to Groups
  • On a separate list, modifiers (diversions) from a Role are stored with UUIDs

API Endpoints

Public Routes (No Auth)

MethodPathHandlerDescription
GET/healthinlineHealth check
POST/api/v1/auth/loginauthHandler.LoginUser login
POST/api/v1/platform/auth/loginplatformAuthHandler.LoginPlatform admin login
POST/api/v1/invites/validateinviteHandler.ValidateValidate invite token
POST/api/v1/invites/acceptinviteHandler.AcceptAccept invite and create account
POST/api/v1/stores/:store_id/auth/pin-loginpinAuthHandler.LoginPIN-based login for store staff

Authenticated Routes

Middleware: Auth(jwtSecret)

MethodPathHandlerDescription
GET/api/v1/auth/meauthHandler.MeGet current user info
POST/api/v1/auth/change-passwordauthHandler.ChangePasswordChange password
GET/api/v1/platform/auth/meplatformAuthHandler.MeGet current platform user info

Platform Routes

Middleware: Auth + PlatformOnly

Superadmin Only

Middleware: + PlatformRole("superadmin")

MethodPathHandlerDescription
GET/api/v1/platform/orgsplatformOrgHandler.ListList organizations
POST/api/v1/platform/orgsplatformOrgHandler.CreateCreate organization
GET/api/v1/platform/orgs/:idplatformOrgHandler.GetGet organization
PUT/api/v1/platform/orgs/:idplatformOrgHandler.UpdateUpdate organization
DELETE/api/v1/platform/orgs/:idplatformOrgHandler.DeleteDelete organization
GET/api/v1/platform/orgs/:id/storesplatformOrgHandler.ListStoresList org stores
GET/api/v1/platform/usersplatformUserHandler.ListList platform users
POST/api/v1/platform/usersplatformUserHandler.CreateCreate platform user
GET/api/v1/platform/users/:idplatformUserHandler.GetGet platform user
PUT/api/v1/platform/users/:idplatformUserHandler.UpdateUpdate platform user
DELETE/api/v1/platform/users/:idplatformUserHandler.DeleteDelete platform user

Superadmin + Support

Middleware: + PlatformRole("superadmin", "support")

MethodPathHandlerDescription
POST/api/v1/platform/impersonateimpersonateHandler.ImpersonateImpersonate org/store user

Organization-Scoped Routes

Base path: /api/v1/orgs/:org_id Middleware: Auth + OrgContext

All Org Members

MethodPathHandlerDescription
GET/orgs/:org_id/membersorgMemberHandler.ListList org members
GET/orgs/:org_id/customersorgCustomerHandler.ListList customers
GET/orgs/:org_id/customers/:customer_idorgCustomerHandler.GetGet customer
POST/orgs/:org_id/customersorgCustomerHandler.CreateCreate customer
PUT/orgs/:org_id/customers/:customer_idorgCustomerHandler.UpdateUpdate customer
POST/orgs/:org_id/customers/:customer_id/pointsorgCustomerHandler.AdjustPointsAdjust loyalty points
GET/orgs/:org_id/categoriescategoryHandler.ListList categories
GET/orgs/:org_id/categories/treecategoryHandler.ListTreeList category tree
GET/orgs/:org_id/categories/:category_idcategoryHandler.GetGet category
GET/orgs/:org_id/supplierssupplierHandler.ListList suppliers
GET/orgs/:org_id/suppliers/:supplier_idsupplierHandler.GetGet supplier
GET/orgs/:org_id/suppliers/:supplier_id/productssupplierHandler.ListProductSuppliersList supplier products
GET/orgs/:org_id/serial-numbersserialNumberHandler.ListList serial numbers
GET/orgs/:org_id/serial-numbers/:serial_idserialNumberHandler.GetGet serial number
GET/orgs/:org_id/serial-numbers/lookup/:serialserialNumberHandler.GetBySerialLookup by serial string
GET/orgs/:org_id/notificationsnotificationHandler.ListList notifications
GET/orgs/:org_id/notifications/unread-countnotificationHandler.CountUnreadCount unread
GET/orgs/:org_id/notifications/:notification_idnotificationHandler.GetGet notification
POST/orgs/:org_id/notifications/:notification_id/readnotificationHandler.MarkReadMark read
POST/orgs/:org_id/notifications/read-allnotificationHandler.MarkAllReadMark all read
GET/orgs/:org_id/promotionspromotionHandler.ListList promotions
GET/orgs/:org_id/promotions/activepromotionHandler.ListActiveList active promotions
GET/orgs/:org_id/promotions/:promotion_idpromotionHandler.GetGet promotion
GET/orgs/:org_id/stock-transfersstockTransferHandler.ListList stock transfers
GET/orgs/:org_id/stock-transfers/:transfer_idstockTransferHandler.GetGet stock transfer

Org Admin (org_owner, org_admin)

Middleware: + RequireOrgRole("org_owner", "org_admin")

MethodPathHandlerDescription
POST/orgs/:org_id/membersorgMemberHandler.AddAdd org member
PUT/orgs/:org_id/members/:user_idorgMemberHandler.UpdateRoleUpdate member role
DELETE/orgs/:org_id/members/:user_idorgMemberHandler.RemoveRemove member
DELETE/orgs/:org_id/customers/:customer_idorgCustomerHandler.DeleteDelete customer
GET/orgs/:org_id/invitesinviteHandler.ListByOrgList org invites
POST/orgs/:org_id/invitesinviteHandler.CreateCreate invite
POST/orgs/:org_id/invites/:invite_id/revokeinviteHandler.RevokeRevoke invite
DELETE/orgs/:org_id/invites/:invite_idinviteHandler.DeleteDelete invite
GET/orgs/:org_id/activity-logactivityLogHandler.ListOrgActivityLogsList org activity
POST/orgs/:org_id/categoriescategoryHandler.CreateCreate category
PUT/orgs/:org_id/categories/:category_idcategoryHandler.UpdateUpdate category
DELETE/orgs/:org_id/categories/:category_idcategoryHandler.DeleteDelete category
POST/orgs/:org_id/supplierssupplierHandler.CreateCreate supplier
PUT/orgs/:org_id/suppliers/:supplier_idsupplierHandler.UpdateUpdate supplier
DELETE/orgs/:org_id/suppliers/:supplier_idsupplierHandler.DeleteDelete supplier
POST/orgs/:org_id/suppliers/:supplier_id/productssupplierHandler.AddProductSupplierLink supplier to product
DELETE/orgs/:org_id/suppliers/:supplier_id/products/:product_idsupplierHandler.RemoveProductSupplierUnlink supplier
POST/orgs/:org_id/serial-numbersserialNumberHandler.CreateCreate serial number
POST/orgs/:org_id/serial-numbers/:serial_id/sellserialNumberHandler.SellMark serial sold
POST/orgs/:org_id/serial-numbers/:serial_id/returnserialNumberHandler.ReturnMark serial returned
POST/orgs/:org_id/notificationsnotificationHandler.CreateCreate notification
POST/orgs/:org_id/promotionspromotionHandler.CreateCreate promotion
PUT/orgs/:org_id/promotions/:promotion_idpromotionHandler.UpdateUpdate promotion
DELETE/orgs/:org_id/promotions/:promotion_idpromotionHandler.DeleteDelete promotion
POST/orgs/:org_id/promotions/:promotion_id/togglepromotionHandler.ToggleActiveToggle active
POST/orgs/:org_id/stock-transfersstockTransferHandler.CreateCreate transfer
POST/orgs/:org_id/stock-transfers/:transfer_id/shipstockTransferHandler.ShipShip transfer
POST/orgs/:org_id/stock-transfers/:transfer_id/receivestockTransferHandler.ReceiveReceive transfer
POST/orgs/:org_id/stock-transfers/:transfer_id/cancelstockTransferHandler.CancelCancel transfer

Store-Scoped Routes

Base path: /api/v1/stores/:store_id Middleware: Auth + StoreContext

All Store Members

MethodPathHandlerDescription
GET/stores/:store_id/membersstoreMemberHandler.ListList store members
GET/stores/:store_id/productsproductHandler.ListList products
GET/stores/:store_id/products/:idproductHandler.GetGet product
GET/stores/:store_id/products/barcode/:barcodeproductHandler.GetByBarcodeGet product by barcode
GET/stores/:store_id/products/typesproductHandler.GetTypesGet product types
GET/stores/:store_id/inventoryinventoryHandler.ListList inventory
GET/stores/:store_id/inventory/:idinventoryHandler.GetStockGet stock level
GET/stores/:store_id/inventory/:id/historyinventoryHandler.GetHistoryGet inventory history
GET/stores/:store_id/transactionstransactionHandler.ListList transactions
GET/stores/:store_id/transactions/:idtransactionHandler.GetGet transaction
GET/stores/:store_id/transactions/summarytransactionHandler.GetSummaryGet summary stats
GET/stores/:store_id/transactions/daily-salestransactionHandler.GetDailySalesGet daily sales
GET/stores/:store_id/discountsdiscountHandler.ListList discounts
GET/stores/:store_id/discounts/:iddiscountHandler.GetGet discount
GET/stores/:store_id/discounts/activediscountHandler.GetActiveGet active discounts
GET/stores/:store_id/returnsreturnHandler.ListList returns
GET/stores/:store_id/returns/:idreturnHandler.GetGet return
GET/stores/:store_id/shifts/preferences/meshiftHandler.GetMyPreferencesGet my shift preferences
POST/stores/:store_id/shifts/preferencesshiftHandler.CreatePreferenceCreate preference
PUT/stores/:store_id/shifts/preferences/:idshiftHandler.UpdatePreferenceUpdate preference
DELETE/stores/:store_id/shifts/preferences/:idshiftHandler.DeletePreferenceDelete preference
GET/stores/:store_id/shifts/assignedshiftHandler.ListAssignedList assigned shifts
GET/stores/:store_id/shifts/assigned/meshiftHandler.GetMyAssignedGet my assigned shifts
GET/stores/:store_id/shifts/statusshiftHandler.GetStatusGet shift status
POST/stores/:store_id/shifts/clock-inshiftHandler.ClockInClock in
POST/stores/:store_id/shifts/clock-outshiftHandler.ClockOutClock out
GET/stores/:store_id/shifts/requestsshiftHandler.ListRequestsList shift requests
POST/stores/:store_id/shifts/requestsshiftHandler.CreateRequestCreate shift request
GET/stores/:store_id/settingssettingsHandler.GetStoreSettingsGet store settings
POST/stores/:store_id/terminals/:id/heartbeatsettingsHandler.TerminalHeartbeatTerminal heartbeat
GET/stores/:store_id/compliance/checkscomplianceHandler.GetChecksGet compliance checks
GET/stores/:store_id/compliance/checks/:check_idcomplianceHandler.GetGet check detail
GET/stores/:store_id/compliance/summarycomplianceHandler.GetSummaryGet compliance summary
POST/stores/:store_id/compliance/verify-agecomplianceHandler.VerifyAgeVerify age
GET/stores/:store_id/tax-configstaxConfigHandler.ListList tax configs
GET/stores/:store_id/tax-configs/activetaxConfigHandler.ListActiveList active configs
GET/stores/:store_id/tax-configs/:config_idtaxConfigHandler.GetGet tax config
GET/stores/:store_id/onboarding/statusonboardingHandler.GetStatusGet onboarding status
POST/stores/:store_id/mkonnekt/skandatamkonnektHandler.GetSkanDataGet mKonnekt SKAN data

Store Manager+ (store_admin, manager)

Middleware: + RequireStoreRole("store_admin", "manager")

MethodPathHandlerDescription
POST/stores/:store_id/productsproductHandler.CreateCreate product
PUT/stores/:store_id/products/:idproductHandler.UpdateUpdate product
POST/stores/:store_id/inventory/receiveinventoryHandler.ReceiveReceive inventory
POST/stores/:store_id/inventory/adjustinventoryHandler.AdjustAdjust inventory
POST/stores/:store_id/inventory/transferinventoryHandler.TransferTransfer inventory
POST/stores/:store_id/transactions/:id/voidtransactionHandler.VoidVoid transaction
POST/stores/:store_id/returnsreturnHandler.CreateCreate return
POST/stores/:store_id/shifts/assignedshiftHandler.CreateAssignedAssign shift
PUT/stores/:store_id/shifts/assigned/:idshiftHandler.UpdateAssignedUpdate assignment
DELETE/stores/:store_id/shifts/assigned/:idshiftHandler.DeleteAssignedDelete assignment
POST/stores/:store_id/shifts/requests/:id/reviewshiftHandler.ReviewRequestReview shift request
POST/stores/:store_id/compliance/overridecomplianceHandler.OverrideOverride compliance check
GET/stores/:store_id/reports/dashboardreportHandler.DashboardDashboard stats
GET/stores/:store_id/reports/salesreportHandler.SalesSales report
GET/stores/:store_id/reports/inventoryreportHandler.InventoryInventory report
GET/stores/:store_id/reports/membersreportHandler.MembersMembers report
POST/stores/:store_id/queryqueryHandler.QueryNL query (symbolic logic)
GET/stores/:store_id/query/schemaqueryHandler.SchemaGet query schema

Store Admin Only

Middleware: + RequireStoreRole("store_admin")

MethodPathHandlerDescription
POST/stores/:store_id/membersstoreMemberHandler.AddAdd store member
PUT/stores/:store_id/members/:user_idstoreMemberHandler.UpdateRoleUpdate member role
DELETE/stores/:store_id/members/:user_idstoreMemberHandler.RemoveRemove member
DELETE/stores/:store_id/products/:idproductHandler.DeleteDelete product
POST/stores/:store_id/discountsdiscountHandler.CreateCreate discount
PUT/stores/:store_id/discounts/:iddiscountHandler.UpdateUpdate discount
DELETE/stores/:store_id/discounts/:iddiscountHandler.DeleteDelete discount
POST/stores/:store_id/discounts/:id/togglediscountHandler.ToggleActiveToggle discount
GET/stores/:store_id/terminalssettingsHandler.ListTerminalsList terminals
GET/stores/:store_id/terminals/:idsettingsHandler.GetTerminalGet terminal
POST/stores/:store_id/terminalssettingsHandler.CreateTerminalCreate terminal
PUT/stores/:store_id/terminals/:idsettingsHandler.UpdateTerminalUpdate terminal
DELETE/stores/:store_id/terminals/:idsettingsHandler.DeleteTerminalDelete terminal
POST/stores/:store_id/terminals/:id/regenerate-secretsettingsHandler.RegenerateTerminalSecretRegenerate secret
PUT/stores/:store_id/settingssettingsHandler.UpdateStoreSettingsUpdate settings
PUT/stores/:store_id/settings/timezonesettingsHandler.UpdateTimezoneUpdate timezone
PUT/stores/:store_id/settings/operating-hourssettingsHandler.UpdateOperatingHoursUpdate hours
POST/stores/:store_id/settings/complete-onboardingsettingsHandler.CompleteOnboardingComplete onboarding
GET/stores/:store_id/activity-logactivityLogHandler.ListActivityLogsList activity logs
GET/stores/:store_id/activity-log/actionsactivityLogHandler.GetActionsGet distinct actions
GET/stores/:store_id/activity-log/entity-typesactivityLogHandler.GetEntityTypesGet entity types
GET/stores/:store_id/activity-log/user/:user_idactivityLogHandler.GetUserActivitySummaryUser activity summary
GET/stores/:store_id/activity-log/:idactivityLogHandler.GetActivityLogGet single log entry
GET/stores/:store_id/invitesinviteHandler.ListByStoreList store invites
POST/stores/:store_id/invitesinviteHandler.CreateCreate invite
POST/stores/:store_id/invites/:invite_id/revokeinviteHandler.RevokeRevoke invite
DELETE/stores/:store_id/invites/:invite_idinviteHandler.DeleteDelete invite
GET/stores/:store_id/compliance/listcomplianceHandler.ListList all compliance
POST/stores/:store_id/tax-configstaxConfigHandler.CreateCreate tax config
PUT/stores/:store_id/tax-configs/:config_idtaxConfigHandler.UpdateUpdate tax config
DELETE/stores/:store_id/tax-configs/:config_idtaxConfigHandler.DeleteDelete tax config
PUT/stores/:store_id/onboarding/phaseonboardingHandler.UpdatePhaseUpdate onboarding phase

Request Body Schemas

Auth

POST /auth/login

{ "email": "string (required)", "password": "string (required)" }

POST /auth/change-password

{
"current_password": "string (required)",
"new_password": "string (required, min=8)"
}

POST /platform/auth/login

{ "email": "string (required)", "password": "string (required)" }

POST /stores/:store_id/auth/pin-login

{ "pin": "string (required)" }

Invites

POST /invites/validate

{ "token": "string (required)" }

POST /invites/accept

{
"token": "string (required)",
"password": "string (required, min=8)",
"first_name": "string (required)",
"last_name": "string (required)"
}

POST /:scope/invites

{
"email": "string (required)",
"first_name": "string",
"last_name": "string",
"org_role": "string",
"store_role": "string",
"store_id": "uuid"
}

Platform

POST /platform/orgs

{ "name": "string (required)", "slug": "string (required)" }

PUT /platform/orgs/:id

{ "name": "string (required)", "slug": "string (required)", "active": "bool" }

POST /platform/users

{
"email": "string (required)",
"password": "string (required, min=8)",
"first_name": "string (required)",
"last_name": "string (required)",
"role": "string (required)"
}

POST /platform/impersonate

{ "org_id": "uuid (required)", "store_id": "uuid (required)" }

Members

POST /orgs/:org_id/members

{
"user_id": "uuid (required)",
"role": "org_owner|org_admin|org_member (required)"
}

POST /stores/:store_id/members

{
"user_id": "uuid (required)",
"role": "store_admin|manager|cashier|stocker (required)",
"clearances": "int"
}

Products

POST/PUT /stores/:store_id/products

{
"barcode": "string (required)",
"name": "string (required)",
"description": "string",
"price": "decimal (required)",
"cost": "decimal (required)",
"over_18": "bool",
"over_21": "bool",
"tax_rate": "decimal",
"stock": "int",
"product_type": "string (required)",
"active": "bool"
}

Inventory

POST /stores/:store_id/inventory/receive

{
"product_id": "uuid (required)",
"quantity": "int (required, >0)",
"notes": "string"
}

POST /stores/:store_id/inventory/adjust

{
"product_id": "uuid (required)",
"quantity": "int (required)",
"reason": "string (required)",
"notes": "string"
}

POST /stores/:store_id/inventory/transfer

{
"product_id": "uuid (required)",
"destination_store_id": "uuid (required)",
"quantity": "int (required, >0)",
"notes": "string"
}

Discounts

POST/PUT /stores/:store_id/discounts

{
"name": "string (required)",
"description": "string",
"start_date": "datetime (required)",
"end_date": "datetime (required)",
"product_id": "uuid",
"product_type": "string",
"discount_type": "percent|fixed (required)",
"amount": "decimal (required)",
"min_purchase": "decimal",
"max_discount": "decimal",
"active": "bool"
}

Returns

POST /stores/:store_id/returns

{
"customer_id": "uuid",
"product_id": "uuid (required)",
"transaction_id": "uuid",
"quantity": "int (required, >0)",
"refund_amount": "decimal (required)",
"reason": "string (required)",
"reason_notes": "string",
"restocked": "bool"
}

Customers

POST/PUT /orgs/:org_id/customers

{
"first_name": "string",
"last_name": "string",
"email": "string",
"phone": "string"
}

POST /orgs/:org_id/customers/:customer_id/points

{ "points": "int (required)" }

Categories

POST /orgs/:org_id/categories

{
"name": "string (required)",
"slug": "string (required)",
"parent_id": "uuid",
"sort_order": "int"
}

Suppliers

POST /orgs/:org_id/suppliers

{
"name": "string (required)",
"contact_email": "string",
"contact_phone": "string"
}

POST /orgs/:org_id/suppliers/:supplier_id/products

{
"supplier_id": "uuid (required)",
"supplier_sku": "string",
"cost": "decimal",
"is_preferred": "bool"
}

Serial Numbers

POST /orgs/:org_id/serial-numbers

{
"store_id": "uuid (required)",
"product_id": "uuid (required)",
"serial_number": "string (required)",
"notes": "string"
}

Promotions

POST /orgs/:org_id/promotions

{
"name": "string (required)",
"description": "string",
"promotion_type": "string (required)",
"buy_quantity": "int (required)",
"get_quantity": "int (required)",
"discount_value": "decimal",
"applies_to_all_stores": "bool",
"start_date": "datetime (required)",
"end_date": "datetime (required)",
"max_uses_per_transaction": "int",
"product_ids": "[uuid]",
"store_ids": "[uuid]"
}

Stock Transfers

POST /orgs/:org_id/stock-transfers

{
"from_store_id": "uuid (required)",
"to_store_id": "uuid (required)",
"notes": "string",
"items": [{ "product_id": "uuid (required)", "quantity": "int (required, >0)" }]
}

POST /orgs/:org_id/stock-transfers/:transfer_id/receive

{
"items": [{ "item_id": "uuid (required)", "received_qty": "int (required, >=0)" }]
}

Compliance

POST /stores/:store_id/compliance/verify-age

{
"product_id": "uuid (required)",
"check_type": "string (required)",
"id_type": "string",
"id_dob": "string",
"id_expiry": "string",
"verified_age": "int",
"required_age": "int (required)"
}

POST /stores/:store_id/compliance/override

{ "check_id": "uuid (required)", "reason": "string (required)" }

Notifications

POST /orgs/:org_id/notifications

{
"store_id": "uuid",
"type": "string (required)",
"title": "string (required)",
"message": "string (required)",
"metadata": "json"
}

Tax Configurations

POST /stores/:store_id/tax-configs

{
"name": "string (required)",
"rate": "decimal (required)",
"applies_to_category": "uuid",
"active": "bool"
}

Shifts

POST /stores/:store_id/shifts/preferences

{
"day_of_week": "int (0-6)",
"start_time": "string (required)",
"end_time": "string (required)",
"priority": "int"
}

POST /stores/:store_id/shifts/assigned

{
"user_id": "uuid (required)",
"shift_date": "string (required)",
"start_time": "string (required)",
"end_time": "string (required)",
"notes": "string"
}

POST /stores/:store_id/shifts/requests

{
"requested_date": "string (required)",
"start_time": "string (required)",
"end_time": "string (required)",
"notes": "string"
}

Settings

PUT /stores/:store_id/settings

{
"name": "string (required)",
"address_line1": "string",
"address_line2": "string",
"city": "string",
"state": "string",
"zip_code": "string",
"phone": "string",
"currency": "string (required)"
}

POST /stores/:store_id/terminals

{ "terminal_name": "string (required)", "is_active": "bool" }

Onboarding

PUT /stores/:store_id/onboarding/phase

{ "phase": "string (required)", "complete": "bool" }

Query

POST /stores/:store_id/query

{
"question": "string (required)",
"history": [{ "role": "string", "content": "string" }]
}

Status Service

The status service is an internal health-check aggregator. It has no authentication and is not exposed to any portal. It is used by uptime monitoring and ops dashboards.

Cloud Run service: pinpointpos-status Port: 8080 Spring application name: myriad-status

GET /

Root health check. Returns the same response as GET /health.

GET /health

Detailed health check. Polls the Cloud Run Admin API for every other service and returns a combined status.

Authentication: None (internal only; restrict via Cloud Run ingress or Cloud Armor).

Response (200):

{
"success": true,
"data": {
"status": "healthy",
"services": {
"merchant-api": "healthy",
"management-api": "healthy",
"terminal-api": "healthy",
"terminal-onboarding": "healthy",
"tx-bundler": "healthy"
}
}
}

status values: healthy (all services healthy) or degraded (one or more services unhealthy or unreachable).

Per-service status values: healthy or unhealthy.

When GOOGLE_CLOUD_PROJECT is not set, health checks are skipped:

{
"success": true,
"data": {
"status": "healthy",
"checks": "skipped",
"reason": "GOOGLE_CLOUD_PROJECT is not configured"
}
}

Internal: CloudRunHealthService

Monitors all other Cloud Run services by calling the Cloud Run Admin API (GET /v2/projects/{project}/locations/{region}/services/{service}).

Monitored services:

  • pinpointpos-merchant-api
  • pinpointpos-management-api
  • pinpointpos-terminal-api
  • pinpointpos-terminal-onboarding
  • pinpointpos-tx-bundler

A service is considered healthy when its latestReadyRevision is non-empty or its terminalCondition.state is CONDITION_SUCCEEDED. All other states (including API errors and timeouts) are reported as unhealthy.

Connection timeout: 3 seconds. Request timeout: 5 seconds.


Endpoint Count Summary

ScopeCount
Public (no auth)6
Authenticated (user)3
Platform (admin)13
Organization-scoped55
Store-scoped93
Total170