Data Act Register / Data Structures

Public schema reference per EU Data Act 2023/2854 Art. 26(b)

This register documents every data field included in the Boncard customer export. It is published before contract conclusion per Art. 26(b) Data Act so customers and destination providers can plan migration in advance. Export endpoints and migration instructions are documented at /data-portability.

1. Schema catalog

All data structures as defined in the internal schema-truth file src/lib/db/types.ts. Every field has its type and description.

Customer Customer (end customer of the tenant)

FieldTypeDescription
idstringnanoid(16) primary key
barbershopIdstringTenant scope (foreign key to Barbershop.id)
firstNamestringCustomer first name (required)
lastNamestring?Customer last name (optional)
phonestring?Phone number, E.164 preferred (optional)
emailstring?Customer email address (optional)
birthdaystring?ISO date YYYY-MM-DD (optional)
notesstring?Free-text notes by owner/staff (optional)
gdprConsentbooleanArt. 6(1)(a) GDPR base consent
marketingConsentbooleanMarketing email consent (double opt-in)
birthdayConsentbooleanBirthday greeting consent (double opt-in)
marketingConsentConfirmedAtstring?ISO timestamp of marketing double opt-in
birthdayConsentConfirmedAtstring?ISO timestamp of birthday double opt-in
unsubscribeTokenstring?OMITTED from export (live credential)
lastMarketingEmailAtstring?ISO timestamp of last marketing email sent
lastBirthdayEmailAtstring?ISO timestamp of last birthday email sent
consentGivenAtstring?ISO timestamp when consent was given
consentSourceenum?CARD_ACTIVATION_FORM | ADMIN_MANUAL_ENTRY | IMPORT | PUBLIC_WEB_FORM
consentIpAddressstring?IP address captured at consent (Art. 7(1) proof)
consentUserAgentstring?User agent captured at consent
isAnonymizedbooleanTrue if personal data has been erased (Art. 17)
createdAtstringISO timestamp record created
updatedAtstringISO timestamp record last updated

Card Card (loyalty card)

FieldTypeDescription
idstringnanoid(16) primary key
barbershopIdstringTenant scope
customerIdstring?Owner of the card (optional until activation)
cardCodestringUnique card code printed on the physical card
statusenumNOT_ACTIVATED | ACTIVE | BLOCKED | LOST | EXPIRED
pointsBalancenumberCurrent points balance
totalPointsEarnednumberLifetime points earned
totalPointsRedeemednumberLifetime points redeemed
activatedAtstring?ISO timestamp of activation
blockedAtstring?ISO timestamp the card was blocked
expiresAtstring?ISO timestamp the card expires
replacedByCardIdstring?If replaced, points to the new card.id
createdAtstringISO timestamp record created
updatedAtstringISO timestamp record last updated

Transaction Transaction (points transaction)

FieldTypeDescription
idstringnanoid(16) primary key
barbershopIdstringTenant scope
cardIdstringCard the points moved on
customerIdstring?Customer reference (denormalized for queries)
userIdstring?Staff/owner who performed the action
typeenumEARN | REDEEM | MANUAL_ADJUSTMENT | EXPIRE | CANCEL
pointsnumberSigned points delta (positive = earn, negative = redeem)
balanceBeforenumberCard balance before this transaction
balanceAfternumberCard balance after this transaction
amountEuronumber?Euro amount of the underlying purchase (for PER_EURO mode)
reasonstringHuman-readable reason (service name, manual reason, etc.)
rewardIdstring?Reward reference when type=REDEEM
metadataobject?Arbitrary key-value metadata for future fields
createdAtstringISO timestamp of the transaction

Service Service (offered service)

FieldTypeDescription
idstringnanoid(16) primary key
barbershopIdstringTenant scope
categoryIdstringForeign key to ServiceCategory.id
namestringService name as shown to staff
descriptionstring?Service description (optional)
priceEurnumberBase price in EUR
pointsAwardnumberPoints granted when this service is delivered
durationMinnumber?Approximate duration in minutes (optional)
sortIndexnumberDisplay ordering within category
activebooleanTrue if currently bookable / shown to staff
createdAtstringISO timestamp record created
updatedAtstringISO timestamp record last updated

Reward Reward (loyalty reward)

FieldTypeDescription
idstringnanoid(16) primary key
barbershopIdstringTenant scope
categoryIdstring?Optional reward category reference
titlestringReward title shown to customers
descriptionstring?Reward description (optional)
pointsCostnumberPoints required to redeem this reward
typeenumDISCOUNT | FREE_SERVICE | GIFT | CUSTOM
discountAmountnumber?Fixed discount in EUR for DISCOUNT type
discountPercentnumber?Percentage discount for DISCOUNT type
activebooleanTrue if currently available for redemption
validFromstring?ISO date — reward available from this date
validUntilstring?ISO date — reward available until this date
maxRedemptionsnumber?Hard cap on total redemptions (optional)
iconNamestring?Curated lucide-react icon key
createdAtstringISO timestamp record created
updatedAtstringISO timestamp record last updated

Redemption Redemption (reward redemption)

FieldTypeDescription
idstringnanoid(16) primary key
barbershopIdstringTenant scope
rewardIdstringReward that was redeemed
cardIdstringCard the points came off
customerIdstringCustomer who redeemed
userIdstring?Staff/owner who confirmed the redemption
pointsSpentnumberPoints debited for this redemption
statusenumCOMPLETED | CANCELLED
cancelledAtstring?ISO timestamp if status=CANCELLED
createdAtstringISO timestamp of the redemption

Barbershop Barbershop (tenant / business entity)

FieldTypeDescription
idstringnanoid(16) primary key
namestringBusiness display name
legalNamestring?Full legal company name (optional)
ownerNamestring?Contact person (optional)
addressstringStreet and house number
postalCodestringPostal code
citystringCity
countrystringISO country code, default DE
phonestringBusiness phone number
emailstringBusiness contact email
websitestring?Business website URL (optional)
logoUrlstring?Logo image URL (R2/CDN)
primaryColorstring?Brand color in hex (default #C9A04A)
pointsPerEuronumberPoints credited per euro spent (PER_EURO mode)
pointsPerVisitnumberPoints credited per visit (PER_VISIT mode)
defaultEarningModeenumPER_EURO | PER_VISIT | MANUAL — default earning mode
currencystringISO 4217 currency code (default EUR)
timezonestringIANA timezone (default Europe/Berlin)
programRulesstring?Public program rules / terms of participation
birthdayMessagestring?Birthday greeting email body
statusenumACTIVE | SUSPENDED | ARCHIVED | SCHEDULED_FOR_DELETION
cardDesignobject?Two-sided card design (front + back + QR placement)
planIdenum?free | pro | enterprise
limitOverridesobject?Per-tenant plan limit overrides
businessHoursarray?Weekly opening hours per weekday
instagramUrlstring?Instagram profile URL
facebookUrlstring?Facebook profile URL
googleMapsUrlstring?Google Maps profile URL
descriptionDestring?Public profile description (German, max 800 chars)
descriptionEnstring?Public profile description (English, max 800 chars)
descriptionUkstring?Public profile description (Ukrainian, max 800 chars)
descriptionRustring?Public profile description (Russian, max 800 chars)
emailSignaturestring?Appended to outgoing marketing/birthday emails (max 500 chars)
autoAnonymizeMonthsnumber?GDPR Art. 5 retention threshold in months (0 = disabled)
autoAnonymizeNotifyDaysstring?Comma-separated days before anonymize (e.g. '30,14,7')
customGdprConsentDestring?Per-tenant override of GDPR consent text (German)
customGdprConsentEnstring?Per-tenant override of GDPR consent text (English)
customGdprConsentUkstring?Per-tenant override of GDPR consent text (Ukrainian)
customGdprConsentRustring?Per-tenant override of GDPR consent text (Russian)
avvAcceptedAtstring?ISO timestamp of AVV (DPA) acceptance
avvAcceptedIpstring?IP address captured at AVV acceptance
avvAcceptedUserAgentstring?User agent captured at AVV acceptance
avvVersionstring?Version of AVV accepted
policyAcceptancesarray?Append-only log of AVV/AUP/AGB/Widerruf/data-act-switching acceptances
createdAtstringISO timestamp record created
updatedAtstringISO timestamp record last updated

2. Export formats

All exports are produced as JSON per RFC 8259, UTF-8 encoded, with 2-space indentation. Schema versions: boncard.tenant.v1 (tenant export, whole business) and boncard.customer.v1 (single end-customer export). Date fields are ISO-8601 strings; optional fields are omitted rather than emitted as null.

3. Interoperability

Points calculation logic: PER_EURO multiplies pointsPerEuro by the transaction amount in euros. PER_VISIT awards pointsPerVisit per visit regardless of amount. MANUAL leaves the points decision to staff at scan time. AVV obligations: before contract conclusion an electronic data processing agreement (Art. 28 GDPR) is concluded; passwords are bcrypt-hashed and audit logs retained 90 days. Retention periods: marketing email events 90 days, transactional 1 year, legal notices 3 years; consent logs 3 years after revocation; deletion-log archive 3 years.

International access & ICT infrastructure (Art. 28(1) Data Act)

Pursuant to Art. 28(1) Regulation (EU) 2023/2854 (Data Act), Boncard discloses the jurisdiction in which the ICT infrastructure used to provide the service is operated (point (a)) and the measures in place against unlawful third-country governmental access to non-personal data (point (b)).

(a) Jurisdiction of the ICT infrastructure

(b) Measures against unlawful third-country governmental access to non-personal data

This disclosure fulfils Art. 28(1)(a)/(b) Data Act. The up-to-date sub-processor list: /subprocessors.

4. Versioning policy

Schema bumps are either backwards-compatible (additional optional fields) or announced 90 days in advance. Active tenants receive a LEGAL_NOTICE email about any material change. The active schema version is included in every export file as the schemaVersion field.

5. Contact and competent authorities

Technical questions about schema and export: sahajaret@gmail.com. Competent authority per Art. 37(1)(a) Data Act: Federal Network Agency (Bundesnetzagentur / BNetzA), Tulpenfeld 4, 53113 Bonn, https://www.bundesnetzagentur.de. Data-protection supervisory authority: State Commissioner for Data Protection and Freedom of Information NRW (LDI NRW), https://www.ldi.nrw.de.

Data Portability (Art. 20 / EU Data Act) · Data Processing Agreement (DPA) · Privacy notice · Sub-processors