medOS Printing
Server-side PDF and Jasper report generation — the only Java service in the stack.
medOS Printing is a standalone Spring Boot (Java) service that renders pixel-faithful documents from JasperReports templates. While the rest of the platform is built on NestJS and Moleculer, report generation lives here because JasperReports is a mature Java library purpose-built for banded, print-ready layouts. The service owns the template library, the rendering pipeline, embedded fonts for non-Latin scripts, and the HTTP endpoints that callers (frontend dialogs, backend services) hit to turn structured data into a downloadable file.
Responsibilities
- Template rendering — fill
.jrxmlJasperReports templates with caller-supplied parameters and tabular rows, then export the result as a streamed document. - Document catalogue — host the bundled template library (prescriptions, stickers, AR/aging/turnaround/daily-cash reports, batch production records, and more).
- Multi-page composition — merge multiple filled reports into a single output document for combined slips or multi-section reports.
- Remote templates — optionally fetch a template by URL (IPFS-hosted) instead of using a bundled file, so report layouts can be versioned outside the service jar.
- Internationalised, print-ready typography — ship embedded Thai and barcode fonts so Thai labels, barcodes, and stickers render correctly without host-font dependencies.
- Auth + caching — guard generation endpoints with token / API-key authentication and cache repeat report fills.
Major modules
| Package / component | Purpose |
|---|---|
controller.PdfController | HTTP entry points for document generation (/{exportType}/create/{templateName}, IPFS template variant, public test route). |
service.PdfService | Core JasperReports engine wrapper — fills a template into a JasperPrint and merges multiple prints. |
service.PdfPrintService | Builds streamable report output from a PrintingRequest, with @Cacheable report caching and direct-to-printer dispatch. |
model.PrintingRequest | Request contract: a docParams map plus a list of TableRow records that populate the template's detail band. |
controller.AuthController / security.* | Login, token issuance, and the token / API-key authentication filters. |
controller.UserController / RoleController | User and role administration for service access. |
config.AppProperties / SecurityConfig / MvcConfig | Spring configuration — externalised properties, security chain, MVC wiring. |
resources/templates/*.jrxml | The bundled JasperReports template library. |
resources/fonts / resources/i18n | Embedded font families (Thai, barcode) and messages_en / messages_th localisation bundles. |
Generation flow
Caller (frontend dialog / backend service)
│ POST /{exportType}/create/{templateName}
│ body: { docParams: {...}, tableRow: [...] }
▼
PdfController ──▶ auth filter (token / API key)
│
▼
PdfPrintService.generatePdfReport() (@Cacheable)
│
▼
PdfService.buildReportJasperPrint()
│ load /templates/<name>.jrxml
│ fill parameters + TableRow data source
▼
JasperPrint ──▶ export ──▶ streamed document
│
▼
InputStreamResource → download / print
Templates can also be sourced remotely: the /create/ipfs/{templateName} variant
resolves the layout from an IPFS URL before filling, allowing template iteration
without redeploying the service.
Request contract
A generation call carries two things — a parameter map applied to the report's header/static fields, and a list of rows that drive the repeating detail band:
{
"docParams": { "patientName": "...", "issuedDate": "..." },
"tableRow": [ { /* row 1 */ }, { /* row 2 */ } ]
}
The exportType and templateName path segments select the output format and the
template (e.g. a prescription, a sticker, or an accounts-receivable report).
Where it fits
The frontend's report dialogs and a number of backend services delegate to this service whenever a print-ready artifact is needed. It is intentionally stateless with respect to clinical data: callers pass the data, Printing renders the layout.
Backend services
Financial, clinical and other NestJS services post structured data to Printing for AR, aging, cash, and clinical slips.
Filestore + IPFS
Remote templates and rendered artifacts can be persisted via the filestore / IPFS layer.
Backend overview
See how the 16 services and the Java reporting service fit together in the mesh.
Config flags
| Concern | Notes |
|---|---|
| Port | Listens on 8088 by default. |
| Spring profiles | Runs under a Spring profile (e.g. development / production) selected at launch. |
| External properties | Service settings (template/IPFS resolution, security) are externalised via AppProperties. |
| Caching | Report fills are cached (@Cacheable("pdfReports")) to avoid re-rendering identical requests. |
Related catalog items
SYS-6— PDF Report PrintingCP-9— Report Designer