Inventory management for a sports shop: items, customers, documents, till with TSE, ski rental, workshop, stocktaking. Replaces a twenty-year-old system with the same way of working – only with the record-keeping that applies today.
It is read standing up, at an angle from the side, and operated with a finger. The till window therefore has its own set of dimensions.
One entry point, one permission check, shared building blocks for lists, forms and printouts.
Seven stages. Two of them – posting authorisation and signature – come from § 146a AO.
| Question | Answer comes from |
|---|---|
| Does the till comply with § 146a (1) AO? | Serial number, access credentials, reachable remote endpoint, registered till. A serial number without access credentials counts as non-compliant. |
| May this transaction be posted? | Training posting, approved emergency sale or compliant till. An approval does not change the conformity status. |
Previously, eleven places in the code answered the same question, some with differing conditions. Today there is one class for each.
Most of the effort goes into record-keeping, not into the checkout itself.
| Requirement | Implementation |
|---|---|
| Individual recording § 146a AO | Every transaction signed, every call logged. |
| Failure documentation | In the event of a fault, checkout continues and the failure is noted on the receipt. |
| Immutability GoBD | Database triggers reject UPDATE and DELETE. Corrections only by cancellation. |
| Proof of integrity GoBD para. 107 ff. | Hash chain over the log, position assigned by the database, with a final seal. |
| Cash book § 146 (4) AO | Withdrawals, deposits, bank runs with their own number. Typing errors are reversed by a counter-entry. |
| Digital interface DSFinV-K | 20 CSV files, index.xml and DTD, checked in-house before submission. |
| Retention | Annual archive as CSV per table with record description and checksums. |
| Mandatory details § 14 UStG | One layout for all document types. Missing details are shown on the document. |
| Data protection | Permission levels per module, checked centrally. Empty customer records are deactivated. |
Two tills posting at the same time caused the chain to fork and triggered a false alarm. That was the real danger: a check that regularly goes off for no reason stops being read. Today the database assigns the chain position, and a final seal closes the chain – which also means that cutting off the last rows is noticed.
The legacy data comes from a system without input validation. The checks work in two stages: record the finding, cross-check against the document records, and correct only when the result is unambiguous.
PHP 8.1 and MySQL, rendered on the server. No framework, no build, no third-party packages. All figures describe the program code, as of 16 August 2026.
| Entry point | Front controller with route table. Module and permission level are attached to the address and checked centrally in the router. |
| Core | Database wrapper, login, session, CSRF protection, views, pagination, audit log, own PSR-4 autoloader. |
| Business logic | 172 service classes by subject area, from the till to the legacy data migration. |
| Views | 161 templates, every output escaped. Print views instead of PDF generation. |
| Database | 92 tables, prepared statements throughout, 96 versioned schema steps, 24 triggers against modification. |
| Tools | 93 command-line programs for migration, reconciliation, diagnostics, backup, archive and deployment. |
Not in live operation. The switchover will take place after full go-live approval.
| Foundation and modules | Done |
| Till security and DSFinV-K | Done |
| Immutability in the database | Done |
| Cash book, cash count, findings log | Done |
| Till screen and design rules | Done |
| Data quality and training mode | In progress |
| Data migration from the legacy system | In progress |
| Connection to the online shop | Open – the write path is deliberately closed |
| Connect signature units | Open – until then the system states that no signing takes place |
This page contains no business data, no screenshots from the live records and no sales figures. All figures describe the program code. The project is shown with the consent of Muskelkater Sport Köln. The self-check in the system is not legal advice.
| Target group | Retailers where sales, rental and workshop come together. |
| Status | In development, not in live operation. |
| Availability | Not a finished product. For a business with a similar profile, a custom implementation is conceivable. |
Questions about the construction, the decisions behind it or how it could carry over to another case.