From fcaf9b74ea4eb809598ec0ae6cc4a3878df53be5 Mon Sep 17 00:00:00 2001 From: mahdahar <89adham@gmail.com> Date: Mon, 16 Feb 2026 14:20:52 +0700 Subject: [PATCH] feat: Restructure OpenAPI documentation with modular components - Add OpenApiDocs controller for serving bundled API docs - Split monolithic api-docs.yaml into modular components/ - Add organized paths/ directory with endpoint definitions - Create bundling scripts (JS, PHP, Python) for merging docs - Add API_DOCS_README.md with documentation guidelines - Update Routes.php for new API documentation endpoints - Update swagger.php view and TestDefSiteModel --- app/Config/Routes.php | 3 + app/Controllers/OpenApiDocs.php | 43 + app/Models/Test/TestDefSiteModel.php | 28 +- app/Views/swagger.php | 2 +- public/API_DOCS_README.md | 162 + public/api-docs.bundled.yaml | 4124 +++++++++++++++ public/api-docs.yaml | 4528 +---------------- public/bundle-api-docs.js | 96 + public/bundle-api-docs.php | 55 + public/bundle-api-docs.py | 97 + public/components/schemas/authentication.yaml | 44 + public/components/schemas/common.yaml | 34 + public/components/schemas/edge-api.yaml | 75 + public/components/schemas/master-data.yaml | 157 + public/components/schemas/orders.yaml | 53 + public/components/schemas/organization.yaml | 59 + public/components/schemas/patient-visit.yaml | 105 + public/components/schemas/patient.yaml | 205 + .../components/schemas/securitySchemes.yaml | 10 + public/components/schemas/specimen.yaml | 132 + public/components/schemas/tests.yaml | 278 + public/components/schemas/valuesets.yaml | 77 + public/paths/authentication.yaml | 167 + public/paths/demo.yaml | 42 + public/paths/edge-api.yaml | 103 + public/paths/master-data.yaml | 59 + public/paths/orders.yaml | 150 + public/paths/organization.yaml | 367 ++ public/paths/patient-visits.yaml | 487 ++ public/paths/patients.yaml | 163 + public/paths/results.yaml | 263 + public/paths/specimen.yaml | 289 ++ public/paths/tests.yaml | 113 + public/paths/valuesets.yaml | 498 ++ 34 files changed, 8642 insertions(+), 4426 deletions(-) create mode 100644 app/Controllers/OpenApiDocs.php create mode 100644 public/API_DOCS_README.md create mode 100644 public/api-docs.bundled.yaml create mode 100644 public/bundle-api-docs.js create mode 100644 public/bundle-api-docs.php create mode 100644 public/bundle-api-docs.py create mode 100644 public/components/schemas/authentication.yaml create mode 100644 public/components/schemas/common.yaml create mode 100644 public/components/schemas/edge-api.yaml create mode 100644 public/components/schemas/master-data.yaml create mode 100644 public/components/schemas/orders.yaml create mode 100644 public/components/schemas/organization.yaml create mode 100644 public/components/schemas/patient-visit.yaml create mode 100644 public/components/schemas/patient.yaml create mode 100644 public/components/schemas/securitySchemes.yaml create mode 100644 public/components/schemas/specimen.yaml create mode 100644 public/components/schemas/tests.yaml create mode 100644 public/components/schemas/valuesets.yaml create mode 100644 public/paths/authentication.yaml create mode 100644 public/paths/demo.yaml create mode 100644 public/paths/edge-api.yaml create mode 100644 public/paths/master-data.yaml create mode 100644 public/paths/orders.yaml create mode 100644 public/paths/organization.yaml create mode 100644 public/paths/patient-visits.yaml create mode 100644 public/paths/patients.yaml create mode 100644 public/paths/results.yaml create mode 100644 public/paths/specimen.yaml create mode 100644 public/paths/tests.yaml create mode 100644 public/paths/valuesets.yaml diff --git a/app/Config/Routes.php b/app/Config/Routes.php index 0bf3fb1..db85d70 100644 --- a/app/Config/Routes.php +++ b/app/Config/Routes.php @@ -24,6 +24,9 @@ $routes->group('api', ['filter' => 'auth'], function ($routes) { // Swagger API Documentation (public - no filters) $routes->add('swagger', 'PagesController::swagger'); +// OpenAPI Specification (server-side merged - public) +$routes->get('api-docs', 'OpenApiDocs::index'); + // V2 Auth API Routes (public - no auth required) $routes->group('v2/auth', function ($routes) { $routes->post('login', 'AuthV2Controller::login'); diff --git a/app/Controllers/OpenApiDocs.php b/app/Controllers/OpenApiDocs.php new file mode 100644 index 0000000..95ccbc5 --- /dev/null +++ b/app/Controllers/OpenApiDocs.php @@ -0,0 +1,43 @@ +response + ->setContentType('application/x-yaml') + ->setHeader('Access-Control-Allow-Origin', '*') + ->setHeader('Access-Control-Allow-Methods', 'GET, OPTIONS') + ->setHeader('Access-Control-Allow-Headers', 'Content-Type') + ->setHeader('Cache-Control', 'no-cache, must-revalidate') + ->setBody($content); + + } catch (\Exception $e) { + log_message('error', 'OpenApiDocs Error: ' . $e->getMessage()); + return $this->response + ->setStatusCode(500) + ->setContentType('application/json') + ->setBody(json_encode([ + 'error' => 'Failed to serve OpenAPI spec', + 'message' => $e->getMessage() + ])); + } + } +} diff --git a/app/Models/Test/TestDefSiteModel.php b/app/Models/Test/TestDefSiteModel.php index e375147..86d3341 100644 --- a/app/Models/Test/TestDefSiteModel.php +++ b/app/Models/Test/TestDefSiteModel.php @@ -32,7 +32,7 @@ class TestDefSiteModel extends BaseModel { protected $useSoftDeletes = true; protected $deletedField = "EndDate"; - public function getTests($siteId = null, $testType = null, $visibleScr = null, $visibleRpt = null, $keyword = null) { + public function getTests($siteId = null, $testType = null, $visibleScr = null, $visibleRpt = null, $search = null, $page = 1, $perPage = 20) { $builder = $this->select("testdefsite.TestSiteID, testdefsite.TestSiteCode, testdefsite.TestSiteName, testdefsite.TestType, testdefsite.SeqScr, testdefsite.SeqRpt, testdefsite.VisibleScr, testdefsite.VisibleRpt, testdefsite.CountStat, testdefsite.StartDate, testdefsite.EndDate") @@ -54,15 +54,33 @@ class TestDefSiteModel extends BaseModel { $builder->where('testdefsite.VisibleRpt', $visibleRpt); } - if ($keyword) { - $builder->like('testdefsite.TestSiteName', $keyword); + if ($search) { + $builder->groupStart() + ->like('testdefsite.TestSiteCode', $search) + ->orLike('testdefsite.TestSiteName', $search) + ->groupEnd(); } - $rows = $builder->orderBy('testdefsite.SeqScr', 'ASC')->findAll(); + // Get total count before pagination + $totalBuilder = clone $builder; + $total = $totalBuilder->countAllResults(); + + // Apply pagination + $offset = ($page - 1) * $perPage; + $rows = $builder->orderBy('testdefsite.SeqScr', 'ASC') + ->limit($perPage, $offset) + ->findAll(); + $rows = ValueSet::transformLabels($rows, [ 'TestType' => 'test_type', ]); - return $rows; + + return [ + 'data' => $rows, + 'pagination' => [ + 'total' => $total + ] + ]; } public function getTest($TestSiteID) { diff --git a/app/Views/swagger.php b/app/Views/swagger.php index b95b664..e08665b 100644 --- a/app/Views/swagger.php +++ b/app/Views/swagger.php @@ -357,7 +357,7 @@ // Initialize Swagger UI const ui = SwaggerUIBundle({ - url: "?v=", + url: "?v=", dom_id: '#swagger-ui', deepLinking: true, presets: [ diff --git a/public/API_DOCS_README.md b/public/API_DOCS_README.md new file mode 100644 index 0000000..511ea71 --- /dev/null +++ b/public/API_DOCS_README.md @@ -0,0 +1,162 @@ +# CLQMS OpenAPI Documentation Structure + +## Overview + +The OpenAPI documentation has been reorganized into a modular structure for better maintainability. + +**Architecture:** Server-side resolution (CodeIgniter 4) +- Modular files in `paths/` and `components/schemas/` directories +- CodeIgniter controller merges files on-the-fly +- Single endpoint `/api-docs` serves complete specification +- No build step or bundling required + +## How It Works + +1. **Modular Development:** Edit files in `paths/` and `components/schemas/` +2. **Server-Side Merge:** `OpenApiDocs` controller loads and merges all files +3. **Single Endpoint:** Access `/api-docs` to get complete merged specification +4. **Cache Support:** Can add caching layer for production + +## Recommended Usage + +**For Swagger UI:** Use the CodeIgniter route `/api-docs` (already configured in `app/Views/swagger.php`) + +**For development:** Edit modular files directly - changes are reflected immediately on next request + +## Structure + + +``` +public/ +├── api-docs.yaml # Main entry point with schema references +├── api-docs.bundled.yaml # Bundled version (use this for Swagger UI) +├── components/ +│ └── schemas/ +│ ├── authentication.yaml +│ ├── common.yaml +│ ├── edge-api.yaml +│ ├── master-data.yaml +│ ├── orders.yaml +│ ├── organization.yaml +│ ├── patient-visit.yaml +│ ├── patient.yaml +│ ├── specimen.yaml +│ ├── tests.yaml +│ └── valuesets.yaml +├── paths/ +│ ├── authentication.yaml +│ ├── demo.yaml +│ ├── edge-api.yaml +│ ├── master-data.yaml +│ ├── orders.yaml +│ ├── organization.yaml +│ ├── patient-visits.yaml +│ ├── patients.yaml +│ ├── results.yaml +│ ├── specimen.yaml +│ ├── tests.yaml +│ └── valuesets.yaml +└── bundle-api-docs.py # Bundler script +``` + +## Architecture + +### Server-Side Resolution + +The application uses a CodeIgniter 4 controller (`app/Controllers/OpenApiDocs.php`) that: +1. Loads `public/api-docs.yaml` (base spec with schemas) +2. Scans `public/paths/*.yaml` files +3. Merges all paths into the base spec +4. Outputs complete YAML response + +### Benefits +- ✅ **No bundling step** - Files merged at runtime +- ✅ **Immediate updates** - Changes reflect immediately +- ✅ **Modular structure** - Separate files by domain +- ✅ **CI4 compatible** - Works with CodeIgniter 4 +- ✅ **Nginx ready** - Can migrate to Nginx later +- ✅ **Cacheable** - Can add caching for production + +## Usage + +### For Development + +Edit files directly: +- **Paths:** `public/paths/*.yaml` +- **Schemas:** `public/components/schemas/*.yaml` + +### For Production/Swagger UI + +**Endpoint:** `http://localhost/clqms01/api-docs` + +The endpoint merges all files server-side and returns a complete OpenAPI specification that Swagger UI can consume. + +## Caching (Optional) + +For production, you can add caching to the `OpenApiDocs` controller: + +```php +// In OpenApiDocs::index() +$cacheKey = 'openapi_spec_' . filemtime(FCPATH . 'api-docs.yaml'); +if ($cached = cache()->get($cacheKey)) { + return $this->response->setBody($cached); +} + +// ... build spec ... + +// Cache for 5 minutes +cache()->save($cacheKey, $yaml, 300); +``` + +## Configuration Update + +Update your application configuration to use the bundled file: + +**PHP (CodeIgniter):** +```php +// Already updated in app/Views/swagger.php: +url: "" +``` + +**JavaScript/Node:** +```javascript +// Change from: +const spec = await fetch('/api-docs.yaml'); + +// To: +const spec = await fetch('/api-docs.bundled.yaml'); +``` + +## Benefits + +1. **Modular**: Each domain has its own file +2. **Maintainable**: Easier to find and update specific endpoints +3. **Team-friendly**: Multiple developers can work on different files +4. **Schema Reuse**: Schemas defined once, referenced everywhere +5. **Better Versioning**: Individual domains can be versioned separately + +## Migration Notes + +- **From bundled to server-side:** Already done! The system now uses server-side resolution. +- **Nginx migration:** When ready to migrate to Nginx, the approach remains the same (CI4 handles the merging). +- **Back to bundling:** If needed, the bundler script is still available: `python bundle-api-docs.py` + +## Troubleshooting + +### Schema Resolution Errors + +If you see errors like "Could not resolve reference", ensure: +1. Schema files exist in `components/schemas/` +2. References use correct relative paths (e.g., `./components/schemas/patient.yaml#/Patient`) +3. You're using the bundled file (`api-docs.bundled.yaml`) for OpenAPI tools + +### Path Resolution Errors + +OpenAPI 3.0 doesn't support external file references for paths. Always use the bundled version for serving the documentation. + +## Migration Notes + +- The original `api-docs.yaml` is preserved with schema references only +- All paths have been moved to individual files in `paths/` directory +- A bundler script merges everything into `api-docs.bundled.yaml` +- Update your application to serve `api-docs.bundled.yaml` instead diff --git a/public/api-docs.bundled.yaml b/public/api-docs.bundled.yaml new file mode 100644 index 0000000..75fc102 --- /dev/null +++ b/public/api-docs.bundled.yaml @@ -0,0 +1,4124 @@ +openapi: 3.1.0 +info: + title: CLQMS - Clinical Laboratory Quality Management System API + description: | + API for Clinical Laboratory Quality Management System supporting patient management, + specimen tracking, test ordering, instrument integration, and laboratory operations. + + **IMPORTANT:** For OpenAPI tools (Swagger UI, Redoc, Postman, etc.), use the bundled file: + `api-docs.bundled.yaml` which contains all paths and schemas merged into one file. + + This file (api-docs.yaml) contains schema references and is meant for development. + The paths are defined in separate files in the `paths/` directory. + version: 1.0.0 + contact: + name: CLQMS API Support + license: + name: Proprietary +servers: + - url: http://localhost/clqms01/ + description: Local development server + - url: https://clqms01-api.services-summit.my.id/ + description: Production server +tags: + - name: Authentication + description: User authentication and session management + - name: Patients + description: Patient registration and management + - name: Patient Visits + description: Patient visit/encounter management + - name: Organization + description: Organization structure (accounts, sites, disciplines, departments, workstations) + - name: Specimen + description: Specimen and container management + - name: Tests + description: Test definitions and test catalog + - name: Orders + description: Laboratory order management + - name: Results + description: Patient results reporting + - name: Edge API + description: Instrument integration endpoints + - name: Master Data + description: Lookup and reference data + - name: ValueSets + description: Value set definitions and items + - name: Demo + description: Demo/test endpoints (no authentication) +paths: + /api/auth/login: + post: + tags: + - Authentication + summary: User login + description: Authenticate user and receive JWT token via HTTP-only cookie + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/LoginRequest' + application/x-www-form-urlencoded: + schema: + $ref: '#/components/schemas/LoginRequest' + responses: + '200': + description: Login successful + headers: + Set-Cookie: + description: JWT token in HTTP-only cookie + schema: + type: string + content: + application/json: + schema: + $ref: '#/components/schemas/LoginResponse' + '400': + description: Missing username + content: + application/json: + schema: + $ref: '#/components/schemas/ErrorResponse' + '401': + description: Invalid credentials + content: + application/json: + schema: + $ref: '#/components/schemas/ErrorResponse' + /api/auth/logout: + post: + tags: + - Authentication + summary: User logout + description: Clear JWT token cookie + security: + - bearerAuth: [] + responses: + '200': + description: Logout successful + content: + application/json: + schema: + $ref: '#/components/schemas/SuccessResponse' + /api/auth/check: + get: + tags: + - Authentication + summary: Check authentication status + security: + - bearerAuth: [] + - cookieAuth: [] + responses: + '200': + description: Authenticated + content: + application/json: + schema: + type: object + properties: + authenticated: + type: boolean + user: + type: object + '401': + description: Not authenticated + /api/auth/register: + post: + tags: + - Authentication + summary: Register new user + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/RegisterRequest' + responses: + '201': + description: User created + content: + application/json: + schema: + $ref: '#/components/schemas/SuccessResponse' + /api/auth/change_pass: + post: + tags: + - Authentication + summary: Change password + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - current_password + - new_password + properties: + current_password: + type: string + format: password + new_password: + type: string + format: password + responses: + '200': + description: Password changed successfully + /v2/auth/login: + post: + tags: + - Authentication + summary: V2 User login + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/LoginRequest' + responses: + '200': + description: Login successful + content: + application/json: + schema: + $ref: '#/components/schemas/LoginResponse' + /v2/auth/logout: + post: + tags: + - Authentication + summary: V2 User logout + responses: + '200': + description: Logout successful + /v2/auth/check: + get: + tags: + - Authentication + summary: V2 Check authentication + responses: + '200': + description: Auth check result + /v2/auth/register: + post: + tags: + - Authentication + summary: V2 Register new user + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/RegisterRequest' + responses: + '201': + description: User created + /api/demo/hello: + get: + tags: + - Demo + summary: Hello world endpoint + description: Simple test endpoint that returns a greeting message + responses: + '200': + description: Successful response + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: Hello, World! + /api/demo/ping: + get: + tags: + - Demo + summary: Ping endpoint + description: Health check endpoint to verify API is running + responses: + '200': + description: API is running + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: pong + timestamp: + type: string + format: date-time + /api/edge/results: + post: + tags: + - Edge API + summary: Receive results from instrument (tiny-edge) + description: | + Receives instrument results and stores them in the edgeres table for processing. + This endpoint is typically called by the tiny-edge middleware connected to laboratory analyzers. + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/EdgeResultRequest' + responses: + '201': + description: Result received and queued + content: + application/json: + schema: + $ref: '#/components/schemas/EdgeResultResponse' + '400': + description: Invalid JSON payload + /api/edge/orders: + get: + tags: + - Edge API + summary: Fetch pending orders for instruments + description: Returns orders that need to be sent to laboratory instruments for testing + parameters: + - name: instrument_id + in: query + schema: + type: string + description: Filter by instrument + - name: status + in: query + schema: + type: string + enum: + - pending + - acknowledged + description: Filter by status + responses: + '200': + description: List of orders + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '#/components/schemas/EdgeOrder' + /api/edge/orders/{orderId}/ack: + post: + tags: + - Edge API + summary: Acknowledge order delivery + description: Mark order as acknowledged by the instrument + parameters: + - name: orderId + in: path + required: true + schema: + type: integer + description: Edge order ID + responses: + '200': + description: Order acknowledged + content: + application/json: + schema: + $ref: '#/components/schemas/SuccessResponse' + /api/edge/status: + post: + tags: + - Edge API + summary: Log instrument status update + description: Receive status updates from laboratory instruments + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - instrument_id + - status + properties: + instrument_id: + type: string + status: + type: string + enum: + - online + - offline + - error + - maintenance + message: + type: string + timestamp: + type: string + format: date-time + responses: + '200': + description: Status logged + /api/location: + get: + tags: + - Master Data + summary: List locations + security: + - bearerAuth: [] + parameters: + - name: LocCode + in: query + schema: + type: string + description: Filter by location code + - name: LocName + in: query + schema: + type: string + description: Filter by location name (searches in LocFull) + responses: + '200': + description: List of locations + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + type: array + items: + $ref: '#/components/schemas/Location' + post: + tags: + - Master Data + summary: Create location + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - LocCode + - LocFull + properties: + SiteID: + type: integer + LocCode: + type: string + maxLength: 6 + Parent: + type: integer + LocFull: + type: string + maxLength: 255 + /api/ordertest: + get: + tags: + - Orders + summary: List orders + security: + - bearerAuth: [] + parameters: + - name: page + in: query + schema: + type: integer + - name: perPage + in: query + schema: + type: integer + - name: InternalPID + in: query + schema: + type: integer + description: Filter by internal patient ID + - name: OrderStatus + in: query + schema: + type: string + enum: + - ORD + - SCH + - ANA + - VER + - REV + - REP + description: | + ORD: Ordered + SCH: Scheduled + ANA: Analysis + VER: Verified + REV: Reviewed + REP: Reported + responses: + '200': + description: List of orders + post: + tags: + - Orders + summary: Create order + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - PatientID + - Tests + properties: + PatientID: + type: string + VisitID: + type: string + Priority: + type: string + enum: + - R + - S + - U + description: | + R: Routine + S: Stat + U: Urgent + SiteID: + type: integer + RequestingPhysician: + type: string + Tests: + type: array + items: + type: object + properties: + TestID: + type: integer + SpecimenType: + type: string + responses: + '201': + description: Order created successfully + patch: + tags: + - Orders + summary: Update order + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/OrderTest' + responses: + '200': + description: Order updated + delete: + tags: + - Orders + summary: Delete order + security: + - bearerAuth: [] + responses: + '200': + description: Order deleted + /api/ordertest/status: + post: + tags: + - Orders + summary: Update order status + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - OrderID + - OrderStatus + properties: + OrderID: + type: string + OrderStatus: + type: string + enum: + - ORD + - SCH + - ANA + - VER + - REV + - REP + description: | + ORD: Ordered + SCH: Scheduled + ANA: Analysis + VER: Verified + REV: Reviewed + REP: Reported + responses: + '200': + description: Order status updated + /api/ordertest/{id}: + get: + tags: + - Orders + summary: Get order by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: string + responses: + '200': + description: Order details + /api/organization/account/{id}: + get: + tags: + - Organization + summary: Get account by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Account details + content: + application/json: + schema: + $ref: '#/components/schemas/Account' + /api/organization/site: + get: + tags: + - Organization + summary: List sites + security: + - bearerAuth: [] + responses: + '200': + description: List of sites + post: + tags: + - Organization + summary: Create site + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/Site' + responses: + '201': + description: Site created + patch: + tags: + - Organization + summary: Update site + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + SiteName: + type: string + SiteCode: + type: string + AccountID: + type: integer + responses: + '200': + description: Site updated + delete: + tags: + - Organization + summary: Delete site + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + responses: + '200': + description: Site deleted + /api/organization/site/{id}: + get: + tags: + - Organization + summary: Get site by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Site details + /api/organization/discipline: + get: + tags: + - Organization + summary: List disciplines + security: + - bearerAuth: [] + responses: + '200': + description: List of disciplines + post: + tags: + - Organization + summary: Create discipline + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/Discipline' + responses: + '201': + description: Discipline created + patch: + tags: + - Organization + summary: Update discipline + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + DisciplineName: + type: string + DisciplineCode: + type: string + responses: + '200': + description: Discipline updated + delete: + tags: + - Organization + summary: Delete discipline + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + responses: + '200': + description: Discipline deleted + /api/organization/discipline/{id}: + get: + tags: + - Organization + summary: Get discipline by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Discipline details + /api/organization/department: + get: + tags: + - Organization + summary: List departments + security: + - bearerAuth: [] + responses: + '200': + description: List of departments + post: + tags: + - Organization + summary: Create department + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/Department' + responses: + '201': + description: Department created + patch: + tags: + - Organization + summary: Update department + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + DeptName: + type: string + DeptCode: + type: string + SiteID: + type: integer + responses: + '200': + description: Department updated + delete: + tags: + - Organization + summary: Delete department + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + responses: + '200': + description: Department deleted + /api/organization/department/{id}: + get: + tags: + - Organization + summary: Get department by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Department details + /api/organization/workstation: + get: + tags: + - Organization + summary: List workstations + security: + - bearerAuth: [] + responses: + '200': + description: List of workstations + post: + tags: + - Organization + summary: Create workstation + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/Workstation' + responses: + '201': + description: Workstation created + patch: + tags: + - Organization + summary: Update workstation + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + WorkstationName: + type: string + WorkstationCode: + type: string + SiteID: + type: integer + DepartmentID: + type: integer + responses: + '200': + description: Workstation updated + delete: + tags: + - Organization + summary: Delete workstation + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + responses: + '200': + description: Workstation deleted + /api/organization/workstation/{id}: + get: + tags: + - Organization + summary: Get workstation by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Workstation details + /api/patvisit: + get: + tags: + - Patient Visits + summary: List patient visits + security: + - bearerAuth: [] + parameters: + - name: page + in: query + schema: + type: integer + - name: perPage + in: query + schema: + type: integer + responses: + '200': + description: List of patient visits + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + type: array + items: + $ref: '#/components/schemas/PatientVisit' + total: + type: integer + description: Total number of records + page: + type: integer + description: Current page number + per_page: + type: integer + description: Number of records per page + post: + tags: + - Patient Visits + summary: Create patient visit + description: | + Creates a new patient visit. PVID is auto-generated with 'DV' prefix if not provided. + Can optionally include PatDiag (diagnosis) and PatVisitADT (ADT information). + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - InternalPID + properties: + PVID: + type: string + description: Visit ID (auto-generated with DV prefix if not provided) + InternalPID: + type: integer + description: Patient ID (required) + EpisodeID: + type: string + description: Episode identifier + SiteID: + type: integer + description: Site reference + PatDiag: + type: object + description: Optional diagnosis information + properties: + DiagCode: + type: string + Diagnosis: + type: string + PatVisitADT: + type: object + description: Optional ADT information + properties: + ADTCode: + type: string + enum: + - A01 + - A02 + - A03 + - A04 + - A08 + LocationID: + type: integer + AttDoc: + type: integer + RefDoc: + type: integer + AdmDoc: + type: integer + CnsDoc: + type: integer + responses: + '201': + description: Visit created successfully + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + type: object + properties: + PVID: + type: string + InternalPVID: + type: integer + patch: + tags: + - Patient Visits + summary: Update patient visit + description: | + Updates an existing patient visit. InternalPVID is required. + Can update main visit data, PatDiag, and add new PatVisitADT records. + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - InternalPVID + properties: + InternalPVID: + type: integer + description: Visit ID (required) + PVID: + type: string + InternalPID: + type: integer + EpisodeID: + type: string + SiteID: + type: integer + PatDiag: + type: object + description: Diagnosis information (will update if exists) + properties: + DiagCode: + type: string + Diagnosis: + type: string + PatVisitADT: + type: array + description: Array of ADT records to add (new records only) + items: + type: object + properties: + ADTCode: + type: string + enum: + - A01 + - A02 + - A03 + - A04 + - A08 + LocationID: + type: integer + AttDoc: + type: integer + RefDoc: + type: integer + AdmDoc: + type: integer + CnsDoc: + type: integer + sequence: + type: integer + description: Used for ordering multiple ADT records + responses: + '200': + description: Visit updated successfully + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + type: object + properties: + PVID: + type: string + InternalPVID: + type: integer + delete: + tags: + - Patient Visits + summary: Delete patient visit + security: + - bearerAuth: [] + responses: + '200': + description: Visit deleted successfully + /api/patvisit/{id}: + get: + tags: + - Patient Visits + summary: Get visit by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: string + description: PVID (visit identifier like DV00001) + responses: + '200': + description: Visit details + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + $ref: '#/components/schemas/PatientVisit' + /api/patvisit/patient/{patientId}: + get: + tags: + - Patient Visits + summary: Get visits by patient ID + security: + - bearerAuth: [] + parameters: + - name: patientId + in: path + required: true + schema: + type: integer + description: Internal Patient ID (InternalPID) + responses: + '200': + description: Patient visits list + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '#/components/schemas/PatientVisit' + /api/patvisitadt: + post: + tags: + - Patient Visits + summary: Create ADT record + description: Create a new Admission/Discharge/Transfer record + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/PatVisitADT' + responses: + '201': + description: ADT record created successfully + content: + application/json: + schema: + $ref: '#/components/schemas/SuccessResponse' + patch: + tags: + - Patient Visits + summary: Update ADT record + description: Update an existing ADT record + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/PatVisitADT' + responses: + '200': + description: ADT record updated successfully + content: + application/json: + schema: + $ref: '#/components/schemas/SuccessResponse' + delete: + tags: + - Patient Visits + summary: Delete ADT visit (soft delete) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - PVADTID + properties: + PVADTID: + type: integer + description: ADT record ID to delete + responses: + '200': + description: ADT visit deleted successfully + /api/patvisitadt/visit/{visitId}: + get: + tags: + - Patient Visits + summary: Get ADT history by visit ID + description: Retrieve the complete Admission/Discharge/Transfer history for a visit, including all locations and doctors + security: + - bearerAuth: [] + parameters: + - name: visitId + in: path + required: true + schema: + type: integer + description: Internal Visit ID (InternalPVID) + responses: + '200': + description: ADT history retrieved successfully + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: ADT history retrieved + data: + type: array + items: + type: object + properties: + PVADTID: + type: integer + InternalPVID: + type: integer + ADTCode: + type: string + enum: + - A01 + - A02 + - A03 + - A04 + - A08 + LocationID: + type: integer + LocationName: + type: string + AttDoc: + type: integer + AttDocFirstName: + type: string + AttDocLastName: + type: string + RefDoc: + type: integer + RefDocFirstName: + type: string + RefDocLastName: + type: string + AdmDoc: + type: integer + AdmDocFirstName: + type: string + AdmDocLastName: + type: string + CnsDoc: + type: integer + CnsDocFirstName: + type: string + CnsDocLastName: + type: string + CreateDate: + type: string + format: date-time + EndDate: + type: string + format: date-time + delete: + tags: + - Patient Visits + summary: Delete ADT visit (soft delete) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - PVADTID + properties: + PVADTID: + type: integer + description: ADT record ID to delete + responses: + '200': + description: ADT visit deleted successfully + /api/patvisitadt/{id}: + get: + tags: + - Patient Visits + summary: Get ADT record by ID + description: Retrieve a single ADT record by its ID, including location and doctor details + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: ADT record ID (PVADTID) + responses: + '200': + description: ADT record retrieved successfully + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: ADT record retrieved + data: + type: object + properties: + PVADTID: + type: integer + InternalPVID: + type: integer + ADTCode: + type: string + enum: + - A01 + - A02 + - A03 + - A04 + - A08 + LocationID: + type: integer + LocationName: + type: string + AttDoc: + type: integer + AttDocFirstName: + type: string + AttDocLastName: + type: string + RefDoc: + type: integer + RefDocFirstName: + type: string + RefDocLastName: + type: string + AdmDoc: + type: integer + AdmDocFirstName: + type: string + AdmDocLastName: + type: string + CnsDoc: + type: integer + CnsDocFirstName: + type: string + CnsDocLastName: + type: string + CreateDate: + type: string + format: date-time + EndDate: + type: string + format: date-time + /api/patient: + get: + tags: + - Patients + summary: List patients + security: + - bearerAuth: [] + parameters: + - name: page + in: query + schema: + type: integer + default: 1 + - name: perPage + in: query + schema: + type: integer + default: 20 + - name: InternalPID + in: query + schema: + type: integer + description: Filter by internal patient ID + - name: PatientID + in: query + schema: + type: string + description: Filter by patient ID + - name: Name + in: query + schema: + type: string + description: Search by patient name + - name: Birthdate + in: query + schema: + type: string + format: date + description: Filter by birthdate (YYYY-MM-DD) + responses: + '200': + description: List of patients + content: + application/json: + schema: + $ref: '#/components/schemas/PatientListResponse' + post: + tags: + - Patients + summary: Create new patient + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/Patient' + responses: + '201': + description: Patient created successfully + content: + application/json: + schema: + $ref: '#/components/schemas/SuccessResponse' + '422': + description: Validation error + content: + application/json: + schema: + $ref: '#/components/schemas/ErrorResponse' + patch: + tags: + - Patients + summary: Update patient + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/Patient' + responses: + '200': + description: Patient updated successfully + delete: + tags: + - Patients + summary: Delete patient (soft delete) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - InternalPID + properties: + InternalPID: + type: integer + description: Internal patient record ID + responses: + '200': + description: Patient deleted successfully + /api/patient/check: + get: + tags: + - Patients + summary: Check if patient exists + security: + - bearerAuth: [] + parameters: + - name: PatientID + in: query + schema: + type: string + description: Patient ID to check + - name: EmailAddress1 + in: query + schema: + type: string + format: email + description: Email address to check + responses: + '200': + description: Patient check result + content: + application/json: + schema: + type: object + properties: + exists: + type: boolean + data: + $ref: '#/components/schemas/Patient' + /api/patient/{id}: + get: + tags: + - Patients + summary: Get patient by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: Internal patient record ID + responses: + '200': + description: Patient details + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + $ref: '#/components/schemas/Patient' + /api/results: + get: + tags: + - Results + summary: Get patient results + description: Retrieve patient test results with optional filters + security: + - bearerAuth: [] + parameters: + - name: InternalPID + in: query + schema: + type: integer + description: Filter by internal patient ID + - name: OrderID + in: query + schema: + type: string + description: Filter by order ID + - name: TestCode + in: query + schema: + type: string + description: Filter by test code + - name: date_from + in: query + schema: + type: string + format: date + description: Filter results from date (YYYY-MM-DD) + - name: date_to + in: query + schema: + type: string + format: date + description: Filter results to date (YYYY-MM-DD) + - name: verified_only + in: query + schema: + type: boolean + default: false + description: Return only verified results + responses: + '200': + description: List of patient results + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + type: object + properties: + ResultID: + type: integer + InternalPID: + type: integer + OrderID: + type: string + TestID: + type: integer + TestCode: + type: string + TestName: + type: string + ResultValue: + type: string + Unit: + type: string + ReferenceRange: + type: string + AbnormalFlag: + type: string + Verified: + type: boolean + VerifiedBy: + type: string + VerifiedDate: + type: string + format: date-time + ResultDate: + type: string + format: date-time + post: + tags: + - Results + summary: Create or update result + description: Create a new result or update an existing result entry + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - InternalPID + - TestID + - ResultValue + properties: + InternalPID: + type: integer + OrderID: + type: string + TestID: + type: integer + ResultValue: + type: string + Unit: + type: string + AbnormalFlag: + type: string + enum: + - H + - L + - 'N' + - A + - C + description: H=High, L=Low, N=Normal, A=Abnormal, C=Critical + responses: + '201': + description: Result created successfully + content: + application/json: + schema: + $ref: '#/components/schemas/SuccessResponse' + /api/results/{id}: + get: + tags: + - Results + summary: Get result by ID + description: Retrieve a specific result entry by its ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: Result ID + responses: + '200': + description: Result details + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: object + properties: + ResultID: + type: integer + InternalPID: + type: integer + OrderID: + type: string + TestID: + type: integer + TestCode: + type: string + TestName: + type: string + ResultValue: + type: string + Unit: + type: string + ReferenceRange: + type: string + AbnormalFlag: + type: string + Verified: + type: boolean + VerifiedBy: + type: string + VerifiedDate: + type: string + format: date-time + ResultDate: + type: string + format: date-time + patch: + tags: + - Results + summary: Update result + description: Update an existing result entry + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: Result ID + requestBody: + required: true + content: + application/json: + schema: + type: object + properties: + ResultValue: + type: string + Unit: + type: string + AbnormalFlag: + type: string + enum: + - H + - L + - 'N' + - A + - C + Verified: + type: boolean + responses: + '200': + description: Result updated successfully + content: + application/json: + schema: + $ref: '#/components/schemas/SuccessResponse' + delete: + tags: + - Results + summary: Delete result + description: Soft delete a result entry + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: Result ID + responses: + '200': + description: Result deleted successfully + content: + application/json: + schema: + $ref: '#/components/schemas/SuccessResponse' + /api/results/{id}/verify: + post: + tags: + - Results + summary: Verify result + description: Mark a result as verified by the current user + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: Result ID + responses: + '200': + description: Result verified successfully + content: + application/json: + schema: + $ref: '#/components/schemas/SuccessResponse' + /api/specimen: + get: + tags: + - Specimen + summary: List specimens + security: + - bearerAuth: [] + responses: + '200': + description: List of specimens + post: + tags: + - Specimen + summary: Create specimen + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/Specimen' + responses: + '201': + description: Specimen created + patch: + tags: + - Specimen + summary: Update specimen + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/Specimen' + responses: + '200': + description: Specimen updated + /api/specimen/{id}: + get: + tags: + - Specimen + summary: Get specimen by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Specimen details + /api/specimen/container: + get: + tags: + - Specimen + summary: List container definitions + security: + - bearerAuth: [] + responses: + '200': + description: List of container definitions + post: + tags: + - Specimen + summary: Create container definition + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/ContainerDef' + responses: + '201': + description: Container definition created + patch: + tags: + - Specimen + summary: Update container definition + security: + - bearerAuth: [] + responses: + '200': + description: Container definition updated + /api/specimen/container/{id}: + get: + tags: + - Specimen + summary: Get container definition by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Container definition details + /api/specimen/containerdef: + get: + tags: + - Specimen + summary: List container definitions (alias) + security: + - bearerAuth: [] + responses: + '200': + description: List of container definitions + post: + tags: + - Specimen + summary: Create container definition (alias) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/ContainerDef' + responses: + '201': + description: Container definition created + patch: + tags: + - Specimen + summary: Update container definition (alias) + security: + - bearerAuth: [] + responses: + '200': + description: Container definition updated + /api/specimen/prep: + get: + tags: + - Specimen + summary: List specimen preparations + security: + - bearerAuth: [] + responses: + '200': + description: List of specimen preparations + post: + tags: + - Specimen + summary: Create specimen preparation + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/SpecimenPrep' + responses: + '201': + description: Specimen preparation created + patch: + tags: + - Specimen + summary: Update specimen preparation + security: + - bearerAuth: [] + responses: + '200': + description: Specimen preparation updated + /api/specimen/prep/{id}: + get: + tags: + - Specimen + summary: Get specimen preparation by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Specimen preparation details + /api/specimen/status: + get: + tags: + - Specimen + summary: List specimen statuses + security: + - bearerAuth: [] + responses: + '200': + description: List of specimen statuses + post: + tags: + - Specimen + summary: Create specimen status + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/SpecimenStatus' + responses: + '201': + description: Specimen status created + patch: + tags: + - Specimen + summary: Update specimen status + security: + - bearerAuth: [] + responses: + '200': + description: Specimen status updated + /api/specimen/status/{id}: + get: + tags: + - Specimen + summary: Get specimen status by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Specimen status details + /api/specimen/collection: + get: + tags: + - Specimen + summary: List specimen collection methods + security: + - bearerAuth: [] + responses: + '200': + description: List of collection methods + post: + tags: + - Specimen + summary: Create specimen collection method + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/SpecimenCollection' + responses: + '201': + description: Collection method created + patch: + tags: + - Specimen + summary: Update specimen collection method + security: + - bearerAuth: [] + responses: + '200': + description: Collection method updated + /api/specimen/collection/{id}: + get: + tags: + - Specimen + summary: Get specimen collection method by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Collection method details + /api/tests: + get: + tags: + - Tests + summary: List test definitions + security: + - bearerAuth: [] + parameters: + - name: page + in: query + schema: + type: integer + default: 1 + description: Page number for pagination + - name: perPage + in: query + schema: + type: integer + default: 20 + description: Number of items per page + - name: SiteID + in: query + schema: + type: integer + description: Filter by site ID + - name: TestType + in: query + schema: + type: string + enum: + - TEST + - PARAM + - CALC + - GROUP + - TITLE + description: Filter by test type + - name: VisibleScr + in: query + schema: + type: integer + enum: + - 0 + - 1 + description: Filter by screen visibility (0=hidden, 1=visible) + - name: VisibleRpt + in: query + schema: + type: integer + enum: + - 0 + - 1 + description: Filter by report visibility (0=hidden, 1=visible) + - name: search + in: query + schema: + type: string + description: Search by test code or name + responses: + '200': + description: List of test definitions + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '#/components/schemas/TestDefinition' + pagination: + type: object + properties: + total: + type: integer + description: Total number of records matching the query + post: + tags: + - Tests + summary: Create test definition + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/TestDefinition' + responses: + '201': + description: Test definition created + patch: + tags: + - Tests + summary: Update test definition + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '#/components/schemas/TestDefinition' + responses: + '200': + description: Test definition updated + /api/tests/{id}: + get: + tags: + - Tests + summary: Get test definition by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Test definition details + /api/valueset: + get: + tags: + - ValueSets + summary: List lib value sets + description: List all library/system value sets from JSON files with item counts. Returns an object where keys are value set names and values are item counts. + security: + - bearerAuth: [] + parameters: + - name: search + in: query + schema: + type: string + description: Optional search term to filter value set names + responses: + '200': + description: List of lib value sets with item counts + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + data: + type: object + additionalProperties: + type: integer + description: Number of items in each value set + example: + sex: 3 + marital_status: 6 + order_status: 6 + /api/valueset/{key}: + get: + tags: + - ValueSets + summary: Get lib value set by key + description: | + Get a specific library/system value set from JSON files. + + **Available value set keys:** + - `activity_result` - Activity Result + - `additive` - Additive + - `adt_event` - ADT Event + - `area_class` - Area Class + - `body_site` - Body Site + - `collection_method` - Collection Method + - `container_cap_color` - Container Cap Color + - `container_class` - Container Class + - `container_size` - Container Size + - `country` - Country + - `death_indicator` - Death Indicator + - `did_type` - DID Type + - `enable_disable` - Enable/Disable + - `entity_type` - Entity Type + - `ethnic` - Ethnic + - `fasting_status` - Fasting Status + - `formula_language` - Formula Language + - `generate_by` - Generate By + - `identifier_type` - Identifier Type + - `location_type` - Location Type + - `marital_status` - Marital Status + - `math_sign` - Math Sign + - `numeric_ref_type` - Numeric Reference Type + - `operation` - Operation (CRUD) + - `order_priority` - Order Priority + - `order_status` - Order Status + - `race` - Race (Ethnicity) + - `range_type` - Range Type + - `reference_type` - Reference Type + - `religion` - Religion + - `requested_entity` - Requested Entity + - `result_type` - Result Type + - `result_unit` - Result Unit + - `sex` - Sex + - `site_class` - Site Class + - `site_type` - Site Type + - `specimen_activity` - Specimen Activity + - `specimen_condition` - Specimen Condition + - `specimen_role` - Specimen Role + - `specimen_status` - Specimen Status + - `specimen_type` - Specimen Type + - `test_activity` - Test Activity + - `test_type` - Test Type + - `text_ref_type` - Text Reference Type + - `unit` - Unit + - `v_category` - VCategory + - `ws_type` - Workstation Type + security: + - bearerAuth: [] + parameters: + - name: key + in: path + required: true + schema: + type: string + enum: + - activity_result + - additive + - adt_event + - area_class + - body_site + - collection_method + - container_cap_color + - container_class + - container_size + - country + - death_indicator + - did_type + - enable_disable + - entity_type + - ethnic + - fasting_status + - formula_language + - generate_by + - identifier_type + - location_type + - marital_status + - math_sign + - numeric_ref_type + - operation + - order_priority + - order_status + - race + - range_type + - reference_type + - religion + - requested_entity + - result_type + - result_unit + - sex + - site_class + - site_type + - specimen_activity + - specimen_condition + - specimen_role + - specimen_status + - specimen_type + - test_activity + - test_type + - text_ref_type + - unit + - v_category + - ws_type + description: Value set key name + responses: + '200': + description: Lib value set details + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '#/components/schemas/ValueSetLibItem' + /api/valueset/refresh: + post: + tags: + - ValueSets + summary: Refresh lib ValueSet cache + description: Clear and reload the library/system ValueSet cache from JSON files. Call this after modifying JSON files in app/Libraries/Data/. + security: + - bearerAuth: [] + responses: + '200': + description: Lib ValueSet cache refreshed + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: Cache cleared + /api/valueset/user/items: + get: + tags: + - ValueSets + summary: List user value set items + description: List value set items from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: VSetID + in: query + schema: + type: integer + description: Filter by ValueSet ID + - name: search + in: query + schema: + type: string + description: Search term to filter by VValue, VDesc, or VSName + - name: param + in: query + schema: + type: string + description: Alternative search parameter (alias for search) + responses: + '200': + description: List of user value set items + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '#/components/schemas/ValueSetItem' + post: + tags: + - ValueSets + summary: Create user value set item + description: Create value set item in database (user-defined) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - VSetID + properties: + SiteID: + type: integer + description: Site reference (default 1) + VSetID: + type: integer + description: Reference to value set definition (required) + VOrder: + type: integer + description: Display order (default 0) + VValue: + type: string + description: The value code + VDesc: + type: string + description: The display description/label + responses: + '201': + description: User value set item created + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + $ref: '#/components/schemas/ValueSetItem' + /api/valueset/user/items/{id}: + get: + tags: + - ValueSets + summary: Get user value set item by ID + description: Get value set item from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: User value set item details + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + $ref: '#/components/schemas/ValueSetItem' + put: + tags: + - ValueSets + summary: Update user value set item + description: Update value set item in database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + requestBody: + required: true + content: + application/json: + schema: + type: object + properties: + SiteID: + type: integer + description: Site reference + VSetID: + type: integer + description: Reference to value set definition + VOrder: + type: integer + description: Display order + VValue: + type: string + description: The value code + VDesc: + type: string + description: The display description/label + responses: + '200': + description: User value set item updated + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + $ref: '#/components/schemas/ValueSetItem' + delete: + tags: + - ValueSets + summary: Delete user value set item + description: Delete value set item from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: User value set item deleted + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + /api/valueset/user/def: + get: + tags: + - ValueSets + summary: List user value set definitions + description: List value set definitions from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: search + in: query + schema: + type: string + description: Optional search term to filter definitions + - name: page + in: query + schema: + type: integer + default: 1 + description: Page number for pagination + - name: limit + in: query + schema: + type: integer + default: 100 + description: Number of items per page + responses: + '200': + description: List of user value set definitions + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '#/components/schemas/ValueSetDef' + meta: + type: object + properties: + total: + type: integer + page: + type: integer + limit: + type: integer + post: + tags: + - ValueSets + summary: Create user value set definition + description: Create value set definition in database (user-defined) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + properties: + SiteID: + type: integer + description: Site reference (default 1) + VSName: + type: string + description: Value set name + VSDesc: + type: string + description: Value set description + responses: + '201': + description: User value set definition created + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + $ref: '#/components/schemas/ValueSetDef' + /api/valueset/user/def/{id}: + get: + tags: + - ValueSets + summary: Get user value set definition by ID + description: Get value set definition from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: User value set definition details + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + $ref: '#/components/schemas/ValueSetDef' + put: + tags: + - ValueSets + summary: Update user value set definition + description: Update value set definition in database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + requestBody: + required: true + content: + application/json: + schema: + type: object + properties: + SiteID: + type: integer + description: Site reference + VSName: + type: string + description: Value set name + VSDesc: + type: string + description: Value set description + responses: + '200': + description: User value set definition updated + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + $ref: '#/components/schemas/ValueSetDef' + delete: + tags: + - ValueSets + summary: Delete user value set definition + description: Delete value set definition from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: User value set definition deleted + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string +components: + securitySchemes: + bearerAuth: + type: http + scheme: bearer + bearerFormat: JWT + description: JWT token from login endpoint + cookieAuth: + type: apiKey + in: cookie + name: token + description: JWT token stored in HTTP-only cookie + schemas: + SuccessResponse: + type: object + properties: + status: + type: string + example: success + message: + type: string + code: + type: integer + example: 200 + ErrorResponse: + type: object + properties: + status: + type: string + example: error + message: + type: string + errors: + type: object + DashboardSummary: + type: object + properties: + pendingOrders: + type: integer + todayResults: + type: integer + criticalResults: + type: integer + activePatients: + type: integer + LoginRequest: + type: object + required: + - username + - password + properties: + username: + type: string + example: labuser01 + password: + type: string + format: password + example: secret123 + LoginResponse: + type: object + properties: + status: + type: string + example: success + code: + type: integer + example: 200 + message: + type: string + example: Login successful + RegisterRequest: + type: object + required: + - username + - password + - email + properties: + username: + type: string + password: + type: string + format: password + email: + type: string + format: email + full_name: + type: string + Patient: + type: object + required: + - PatientID + - Sex + - NameFirst + - Birthdate + properties: + PatientID: + type: string + maxLength: 30 + pattern: ^[A-Za-z0-9]+$ + description: Internal patient identifier + AlternatePID: + type: string + maxLength: 30 + pattern: ^[A-Za-z0-9]+$ + Prefix: + type: string + maxLength: 10 + enum: + - Mr + - Mrs + - Ms + - Dr + - Prof + Sex: + type: string + enum: + - '1' + - '2' + description: '1: Female, 2: Male' + NameFirst: + type: string + minLength: 1 + maxLength: 60 + pattern: ^[A-Za-z'\. ]+$ + NameMiddle: + type: string + minLength: 1 + maxLength: 60 + NameMaiden: + type: string + minLength: 1 + maxLength: 60 + NameLast: + type: string + minLength: 1 + maxLength: 60 + Suffix: + type: string + maxLength: 10 + Birthdate: + type: string + format: date-time + description: ISO 8601 UTC datetime + PlaceOfBirth: + type: string + maxLength: 100 + Citizenship: + type: string + maxLength: 100 + Street_1: + type: string + maxLength: 255 + Street_2: + type: string + maxLength: 255 + Street_3: + type: string + maxLength: 255 + ZIP: + type: string + maxLength: 10 + pattern: ^[0-9]+$ + Phone: + type: string + pattern: ^\+?[0-9]{8,15}$ + MobilePhone: + type: string + pattern: ^\+?[0-9]{8,15}$ + EmailAddress1: + type: string + format: email + maxLength: 100 + EmailAddress2: + type: string + format: email + maxLength: 100 + PatIdt: + $ref: '#/components/schemas/PatientIdentifier' + LinkTo: + type: array + description: Array of linked patient references + items: + $ref: '#/components/schemas/LinkedPatient' + Custodian: + $ref: '#/components/schemas/Custodian' + DeathIndicator: + type: string + enum: + - 'Y' + - 'N' + description: 'Y: Yes (deceased), N: No (alive)' + TimeOfDeath: + type: string + format: date-time + description: ISO 8601 UTC datetime of death + PatCom: + type: string + description: Patient comment/notes + PatAtt: + type: array + description: Patient address entries + items: + $ref: '#/components/schemas/PatAttEntry' + Province: + type: integer + description: Province AreaGeoID (foreign key to areageo table) + ProvinceLabel: + type: string + description: Province name (resolved from areageo) + City: + type: integer + description: City AreaGeoID (foreign key to areageo table) + CityLabel: + type: string + description: City name (resolved from areageo) + Country: + type: string + maxLength: 10 + description: Country ISO 3-letter code (e.g., IDN, USA) + CountryLabel: + type: string + description: Country name (resolved from valueset) + Race: + type: string + maxLength: 100 + MaritalStatus: + type: string + enum: + - A + - B + - D + - M + - S + - W + description: 'A: Annulled, B: Separated, D: Divorced, M: Married, S: Single, W: Widowed' + Religion: + type: string + maxLength: 100 + Ethnic: + type: string + maxLength: 100 + PatientIdentifier: + type: object + properties: + IdentifierType: + type: string + enum: + - KTP + - PASS + - SSN + - SIM + - KTAS + description: | + KTP: 16 digit numeric + PASS: alphanumeric max 9 + SSN: 9 digit numeric + SIM: 19-20 digit numeric + KTAS: 11 digit numeric + Identifier: + type: string + maxLength: 255 + LinkedPatient: + type: object + description: Linked patient reference + properties: + InternalPID: + type: integer + description: Internal patient ID of the linked patient + PatientID: + type: string + description: Patient ID of the linked patient + Custodian: + type: object + description: Patient custodian/guardian + properties: + InternalPID: + type: integer + description: Internal patient ID of the custodian + PatientID: + type: string + description: Patient ID of the custodian + PatAttEntry: + type: object + description: Patient address/attorney entry + properties: + Address: + type: string + description: Address text + PatientListResponse: + type: object + properties: + status: + type: string + example: success + data: + type: array + items: + $ref: '#/components/schemas/Patient' + pagination: + type: object + properties: + page: + type: integer + perPage: + type: integer + total: + type: integer + PatientVisit: + type: object + properties: + InternalPVID: + type: integer + description: Primary key (auto-generated) + PVID: + type: string + description: Visit ID (auto-generated with DV prefix if not provided) + InternalPID: + type: integer + description: Reference to patient + EpisodeID: + type: string + description: Episode identifier + SiteID: + type: integer + description: Site reference + CreateDate: + type: string + format: date-time + EndDate: + type: string + format: date-time + ArchivedDate: + type: string + format: date-time + DelDate: + type: string + format: date-time + PatDiag: + type: object + description: Diagnosis information (optional) + properties: + DiagCode: + type: string + Diagnosis: + type: string + PatVisitADT: + type: object + description: ADT (Admission/Discharge/Transfer) information (optional) + properties: + ADTCode: + type: string + enum: + - A01 + - A02 + - A03 + - A04 + - A08 + LocationID: + type: integer + AttDoc: + type: integer + description: Attending physician ContactID + RefDoc: + type: integer + description: Referring physician ContactID + AdmDoc: + type: integer + description: Admitting physician ContactID + CnsDoc: + type: integer + description: Consulting physician ContactID + PatVisitADT: + type: object + properties: + PVADTID: + type: integer + description: Primary key (auto-generated) + InternalPVID: + type: integer + description: Reference to patient visit + ADTCode: + type: string + enum: + - A01 + - A02 + - A03 + - A04 + - A08 + description: | + A01: Admit + A02: Transfer + A03: Discharge + A04: Register + A08: Update + LocationID: + type: integer + description: Location/ward reference + AttDoc: + type: integer + description: Attending physician ContactID + RefDoc: + type: integer + description: Referring physician ContactID + AdmDoc: + type: integer + description: Admitting physician ContactID + CnsDoc: + type: integer + description: Consulting physician ContactID + CreateDate: + type: string + format: date-time + EndDate: + type: string + format: date-time + ArchivedDate: + type: string + format: date-time + DelDate: + type: string + format: date-time + Account: + type: object + properties: + id: + type: integer + AccountName: + type: string + AccountCode: + type: string + AccountType: + type: string + Site: + type: object + properties: + id: + type: integer + SiteName: + type: string + SiteCode: + type: string + AccountID: + type: integer + Discipline: + type: object + properties: + id: + type: integer + DisciplineName: + type: string + DisciplineCode: + type: string + Department: + type: object + properties: + id: + type: integer + DeptName: + type: string + DeptCode: + type: string + SiteID: + type: integer + Workstation: + type: object + properties: + id: + type: integer + WorkstationName: + type: string + WorkstationCode: + type: string + SiteID: + type: integer + DepartmentID: + type: integer + Specimen: + type: object + properties: + id: + type: integer + SpecimenID: + type: string + PatientID: + type: string + SpecimenType: + type: string + description: Specimen type code + SpecimenTypeLabel: + type: string + description: Specimen type display text + CollectionDate: + type: string + format: date-time + CollectionMethod: + type: string + description: Collection method code + CollectionMethodLabel: + type: string + description: Collection method display text + ContainerID: + type: integer + SpecimenStatus: + type: string + description: Specimen status code + SpecimenStatusLabel: + type: string + description: Specimen status display text + BodySite: + type: string + description: Body site code + BodySiteLabel: + type: string + description: Body site display text + ContainerDef: + type: object + properties: + id: + type: integer + ContainerCode: + type: string + ContainerName: + type: string + ConCategory: + type: string + description: Container category code + ConCategoryLabel: + type: string + description: Container category display text + ConSize: + type: string + description: Container size code + ConSizeLabel: + type: string + description: Container size display text + CapColor: + type: string + description: Cap color code + CapColorLabel: + type: string + description: Cap color display text + SpecimenPrep: + type: object + properties: + id: + type: integer + PrepCode: + type: string + PrepName: + type: string + Description: + type: string + SpecimenStatus: + type: object + properties: + id: + type: integer + StatusCode: + type: string + StatusName: + type: string + Description: + type: string + Status: + type: string + description: Status code + StatusLabel: + type: string + description: Status display text + Activity: + type: string + description: Activity code + ActivityLabel: + type: string + description: Activity display text + SpecimenCollection: + type: object + properties: + id: + type: integer + CollectionCode: + type: string + CollectionName: + type: string + Description: + type: string + CollectionMethod: + type: string + description: Collection method code + CollectionMethodLabel: + type: string + description: Collection method display text + Additive: + type: string + description: Additive code + AdditiveLabel: + type: string + description: Additive display text + SpecimenRole: + type: string + description: Specimen role code + SpecimenRoleLabel: + type: string + description: Specimen role display text + TestDefinition: + type: object + properties: + id: + type: integer + TestCode: + type: string + TestName: + type: string + TestType: + type: string + enum: + - TEST + - PARAM + - CALC + - GROUP + - TITLE + description: | + TEST: Technical test + PARAM: Parameter + CALC: Calculated + GROUP: Panel/Profile + TITLE: Section header + DisciplineID: + type: integer + DisciplineName: + type: string + DepartmentID: + type: integer + DepartmentName: + type: string + Unit: + type: string + Formula: + type: string + refnum: + type: array + description: Numeric reference ranges (optional). Mutually exclusive with reftxt - a test can only have ONE reference type. + items: + type: object + properties: + RefNumID: + type: integer + NumRefType: + type: string + enum: + - NMRC + - THOLD + description: NMRC=Numeric range, THOLD=Threshold + NumRefTypeLabel: + type: string + RangeType: + type: string + RangeTypeLabel: + type: string + Sex: + type: string + SexLabel: + type: string + LowSign: + type: string + LowSignLabel: + type: string + HighSign: + type: string + HighSignLabel: + type: string + High: + type: number + format: float + Low: + type: number + format: float + AgeStart: + type: integer + AgeEnd: + type: integer + Flag: + type: string + Interpretation: + type: string + reftxt: + type: array + description: Text reference ranges (optional). Mutually exclusive with refnum - a test can only have ONE reference type. + items: + type: object + properties: + RefTxtID: + type: integer + TxtRefType: + type: string + enum: + - TEXT + - VSET + description: TEXT=Free text, VSET=Value set + TxtRefTypeLabel: + type: string + Sex: + type: string + SexLabel: + type: string + AgeStart: + type: integer + AgeEnd: + type: integer + RefTxt: + type: string + Flag: + type: string + examples: + $1: + Unit: mg/dL + refnum: + - RefNumID: 1 + NumRefType: NMRC + NumRefTypeLabel: Numeric + RangeType: REF + RangeTypeLabel: Reference Range + Sex: '2' + SexLabel: Male + LowSign: GE + LowSignLabel: '>=' + HighSign: LE + HighSignLabel: <= + Low: 70 + High: 100 + AgeStart: 18 + AgeEnd: 99 + Flag: 'N' + Interpretation: Normal + TEST_numeric_thold: + summary: Technical test - threshold reference (THOLD) + value: + id: 1 + TestCode: GLU + TestName: Glucose + TestType: TEST + DisciplineID: 1 + DepartmentID: 1 + Unit: mg/dL + refnum: + - RefNumID: 2 + NumRefType: THOLD + NumRefTypeLabel: Threshold + RangeType: PANIC + RangeTypeLabel: Panic Range + Sex: '1' + SexLabel: Female + LowSign: LT + LowSignLabel: < + High: 40 + AgeStart: 0 + AgeEnd: 120 + Flag: L + Interpretation: Critical Low + $2: + Unit: null + reftxt: + - RefTxtID: 1 + TxtRefType: TEXT + TxtRefTypeLabel: Text + Sex: '2' + SexLabel: Male + AgeStart: 18 + AgeEnd: 99 + RefTxt: NORM=Normal;HYPO=Hypochromic;MACRO=Macrocytic + Flag: 'N' + TEST_text_vset: + summary: Technical test - text reference (VSET) + value: + id: 1 + TestCode: STAGE + TestName: Disease Stage + TestType: TEST + DisciplineID: 1 + DepartmentID: 1 + Unit: null + reftxt: + - RefTxtID: 2 + TxtRefType: VSET + TxtRefTypeLabel: Value Set + Sex: '1' + SexLabel: Female + AgeStart: 0 + AgeEnd: 120 + RefTxt: STG1=Stage 1;STG2=Stage 2;STG3=Stage 3;STG4=Stage 4 + Flag: 'N' + PARAM: + summary: Parameter - no reference range allowed + value: + id: 2 + TestCode: GLU_FAST + TestName: Fasting Glucose + TestType: PARAM + DisciplineID: 1 + DepartmentID: 1 + Unit: mg/dL + $3: + Unit: null + Formula: BUN / Creatinine + refnum: + - RefNumID: 5 + NumRefType: NMRC + NumRefTypeLabel: Numeric + RangeType: REF + RangeTypeLabel: Reference Range + Sex: '1' + SexLabel: Female + LowSign: GE + LowSignLabel: '>=' + HighSign: LE + HighSignLabel: <= + Low: 10 + High: 20 + AgeStart: 18 + AgeEnd: 120 + Flag: 'N' + Interpretation: Normal + $4: + Unit: null + Formula: BUN / Creatinine + refnum: + - RefNumID: 6 + NumRefType: THOLD + NumRefTypeLabel: Threshold + RangeType: PANIC + RangeTypeLabel: Panic Range + Sex: '1' + SexLabel: Female + LowSign: GT + LowSignLabel: '>' + Low: 20 + AgeStart: 18 + AgeEnd: 120 + Flag: H + Interpretation: Elevated - possible prerenal cause + GROUP: + summary: Panel/Profile - no reference range allowed + value: + id: 4 + TestCode: LIPID + TestName: Lipid Panel + TestType: GROUP + DisciplineID: 1 + DepartmentID: 1 + Unit: null + TITLE: + summary: Section header - no reference range allowed + value: + id: 5 + TestCode: CHEM_HEADER + TestName: '--- CHEMISTRY ---' + TestType: TITLE + DisciplineID: 1 + DepartmentID: 1 + Unit: null + TestMap: + type: object + properties: + id: + type: integer + TestMapID: + type: integer + TestCode: + type: string + HostCode: + type: string + HostName: + type: string + ClientCode: + type: string + ClientName: + type: string + HostType: + type: string + description: Host type code + HostTypeLabel: + type: string + description: Host type display text + ClientType: + type: string + description: Client type code + ClientTypeLabel: + type: string + description: Client type display text + OrderTest: + type: object + properties: + OrderID: + type: string + PatientID: + type: string + VisitID: + type: string + OrderDate: + type: string + format: date-time + OrderStatus: + type: string + enum: + - ORD + - SCH + - ANA + - VER + - REV + - REP + description: | + ORD: Ordered + SCH: Scheduled + ANA: Analysis + VER: Verified + REV: Reviewed + REP: Reported + OrderStatusLabel: + type: string + description: Order status display text + Priority: + type: string + enum: + - R + - S + - U + description: | + R: Routine + S: Stat + U: Urgent + PriorityLabel: + type: string + description: Priority display text + SiteID: + type: integer + RequestingPhysician: + type: string + OrderItem: + type: object + properties: + id: + type: integer + OrderID: + type: string + TestID: + type: integer + SpecimenID: + type: string + Status: + type: string + EdgeResultRequest: + type: object + required: + - sample_id + - instrument_id + properties: + sample_id: + type: string + description: Sample barcode/identifier + instrument_id: + type: string + description: Instrument identifier + patient_id: + type: string + description: Patient identifier (optional) + results: + type: array + items: + type: object + properties: + test_code: + type: string + result_value: + type: string + unit: + type: string + flags: + type: string + enum: + - H + - L + - 'N' + - A + description: H=High, L=Low, N=Normal, A=Abnormal + EdgeResultResponse: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: Result received and queued + data: + type: object + properties: + edge_res_id: + type: integer + sample_id: + type: string + instrument_id: + type: string + EdgeOrder: + type: object + properties: + OrderID: + type: string + PatientID: + type: string + SampleID: + type: string + Tests: + type: array + items: + type: object + properties: + TestCode: + type: string + TestName: + type: string + SpecimenType: + type: string + Priority: + type: string + DueDateTime: + type: string + format: date-time + ValueSetLibItem: + type: object + description: Library/system value set item from JSON files + properties: + value: + type: string + description: The value/key code + label: + type: string + description: The display label + ValueSetDef: + type: object + description: User-defined value set definition (from database) + properties: + VSetID: + type: integer + description: Primary key + SiteID: + type: integer + description: Site reference + VSName: + type: string + description: Value set name + VSDesc: + type: string + description: Value set description + CreateDate: + type: string + format: date-time + description: Creation timestamp + EndDate: + type: string + format: date-time + nullable: true + description: Soft delete timestamp + ItemCount: + type: integer + description: Number of items in this value set + ValueSetItem: + type: object + description: User-defined value set item (from database) + properties: + VID: + type: integer + description: Primary key + SiteID: + type: integer + description: Site reference + VSetID: + type: integer + description: Reference to value set definition + VOrder: + type: integer + description: Display order + VValue: + type: string + description: The value code + VDesc: + type: string + description: The display description/label + VCategory: + type: string + description: Category code + CreateDate: + type: string + format: date-time + description: Creation timestamp + EndDate: + type: string + format: date-time + nullable: true + description: Soft delete timestamp + VSName: + type: string + description: Value set name (from joined definition) + Location: + type: object + properties: + LocationID: + type: integer + description: Primary key + SiteID: + type: integer + description: Reference to site + LocCode: + type: string + maxLength: 6 + description: Location code (short identifier) + Parent: + type: integer + nullable: true + description: Parent location ID for hierarchical locations + LocFull: + type: string + maxLength: 255 + description: Full location name + Description: + type: string + maxLength: 255 + description: Location description + LocType: + type: string + description: Location type code (e.g., ROOM, WARD, BUILDING) + CreateDate: + type: string + format: date-time + EndDate: + type: string + format: date-time + nullable: true + Contact: + type: object + properties: + ContactID: + type: integer + description: Primary key + NameFirst: + type: string + description: First name (required) + NameLast: + type: string + description: Last name + Title: + type: string + description: Title (e.g., Dr, Mr, Mrs) + Initial: + type: string + description: Middle initial + Birthdate: + type: string + format: date-time + description: Date of birth + EmailAddress1: + type: string + format: email + description: Primary email address + EmailAddress2: + type: string + format: email + description: Secondary email address + Phone: + type: string + description: Primary phone number + MobilePhone1: + type: string + description: Primary mobile number + MobilePhone2: + type: string + description: Secondary mobile number + Specialty: + type: string + description: Medical specialty code + SubSpecialty: + type: string + description: Sub-specialty code + CreateDate: + type: string + format: date-time + EndDate: + type: string + format: date-time + description: Occupation display text + Occupation: + type: object + properties: + OccupationID: + type: integer + description: Primary key + OccCode: + type: string + description: Occupation code + OccText: + type: string + description: Occupation name/text + Description: + type: string + description: Additional description + CreateDate: + type: string + format: date-time + MedicalSpecialty: + type: object + properties: + SpecialtyID: + type: integer + description: Primary key + SpecialtyText: + type: string + description: Specialty name/text + Parent: + type: integer + description: Parent specialty ID for hierarchical structure + Title: + type: string + description: Title/abbreviation + CreateDate: + type: string + format: date-time + EndDate: + type: string + format: date-time + Counter: + type: object + properties: + CounterID: + type: integer + description: Primary key + CounterDesc: + type: string + description: Counter description/name + CounterValue: + type: integer + description: Current counter value + CounterStart: + type: integer + description: Starting value for the counter + CounterEnd: + type: integer + description: Ending value (for auto-reset) + CounterReset: + type: string + description: Reset pattern (e.g., D=Daily, M=Monthly, Y=Yearly) + CreateDate: + type: string + format: date-time + EndDate: + type: string + format: date-time diff --git a/public/api-docs.yaml b/public/api-docs.yaml index e8e33df..378b662 100644 --- a/public/api-docs.yaml +++ b/public/api-docs.yaml @@ -1,9 +1,15 @@ -openapi: 3.0.3 +openapi: 3.1.0 info: title: CLQMS - Clinical Laboratory Quality Management System API description: | API for Clinical Laboratory Quality Management System supporting patient management, specimen tracking, test ordering, instrument integration, and laboratory operations. + + **IMPORTANT:** For OpenAPI tools (Swagger UI, Redoc, Postman, etc.), use the bundled file: + `api-docs.bundled.yaml` which contains all paths and schemas merged into one file. + + This file (api-docs.yaml) contains schema references and is meant for development. + The paths are defined in separate files in the `paths/` directory. version: 1.0.0 contact: name: CLQMS API Support @@ -56,4425 +62,107 @@ components: description: JWT token stored in HTTP-only cookie schemas: - # Common Schemas + # Common schemas SuccessResponse: - type: object - properties: - status: - type: string - example: success - message: - type: string - code: - type: integer - example: 200 - + $ref: './components/schemas/common.yaml#/SuccessResponse' ErrorResponse: - type: object - properties: - status: - type: string - example: error - message: - type: string - errors: - type: object - - # Authentication - LoginRequest: - type: object - required: - - username - - password - properties: - username: - type: string - example: labuser01 - password: - type: string - format: password - example: secret123 - - LoginResponse: - type: object - properties: - status: - type: string - example: success - code: - type: integer - example: 200 - message: - type: string - example: Login successful - - RegisterRequest: - type: object - required: - - username - - password - - email - properties: - username: - type: string - password: - type: string - format: password - email: - type: string - format: email - full_name: - type: string - - # Patient - PatientIdentifier: - type: object - properties: - IdentifierType: - type: string - enum: [KTP, PASS, SSN, SIM, KTAS] - description: | - KTP: 16 digit numeric - PASS: alphanumeric max 9 - SSN: 9 digit numeric - SIM: 19-20 digit numeric - KTAS: 11 digit numeric - Identifier: - type: string - maxLength: 255 - - LinkedPatient: - type: object - description: Linked patient reference - properties: - InternalPID: - type: integer - description: Internal patient ID of the linked patient - PatientID: - type: string - description: Patient ID of the linked patient - - Custodian: - type: object - description: Patient custodian/guardian - properties: - InternalPID: - type: integer - description: Internal patient ID of the custodian - PatientID: - type: string - description: Patient ID of the custodian - - PatAttEntry: - type: object - description: Patient address/attorney entry - properties: - Address: - type: string - description: Address text - - Patient: - type: object - required: - - PatientID - - Sex - - NameFirst - - Birthdate - properties: - PatientID: - type: string - maxLength: 30 - pattern: '^[A-Za-z0-9]+$' - description: Internal patient identifier - AlternatePID: - type: string - maxLength: 30 - pattern: '^[A-Za-z0-9]+$' - Prefix: - type: string - maxLength: 10 - enum: [Mr, Mrs, Ms, Dr, Prof] - Sex: - type: string - enum: ['1', '2'] - description: '1: Female, 2: Male' - NameFirst: - type: string - minLength: 1 - maxLength: 60 - pattern: "^[A-Za-z'\\. ]+$" - NameMiddle: - type: string - minLength: 1 - maxLength: 60 - NameMaiden: - type: string - minLength: 1 - maxLength: 60 - NameLast: - type: string - minLength: 1 - maxLength: 60 - Suffix: - type: string - maxLength: 10 - Birthdate: - type: string - format: date-time - description: ISO 8601 UTC datetime - PlaceOfBirth: - type: string - maxLength: 100 - Citizenship: - type: string - maxLength: 100 - Street_1: - type: string - maxLength: 255 - Street_2: - type: string - maxLength: 255 - Street_3: - type: string - maxLength: 255 - ZIP: - type: string - maxLength: 10 - pattern: '^[0-9]+$' - Phone: - type: string - pattern: "^\\+?[0-9]{8,15}$" - MobilePhone: - type: string - pattern: "^\\+?[0-9]{8,15}$" - EmailAddress1: - type: string - format: email - maxLength: 100 - EmailAddress2: - type: string - format: email - maxLength: 100 - PatIdt: - $ref: '#/components/schemas/PatientIdentifier' - LinkTo: - type: array - description: Array of linked patient references - items: - $ref: '#/components/schemas/LinkedPatient' - Custodian: - $ref: '#/components/schemas/Custodian' - DeathIndicator: - type: string - enum: [Y, N] - description: 'Y: Yes (deceased), N: No (alive)' - TimeOfDeath: - type: string - format: date-time - description: ISO 8601 UTC datetime of death - PatCom: - type: string - description: Patient comment/notes - PatAtt: - type: array - description: Patient address entries - items: - $ref: '#/components/schemas/PatAttEntry' - Province: - type: integer - description: Province AreaGeoID (foreign key to areageo table) - ProvinceLabel: - type: string - description: Province name (resolved from areageo) - City: - type: integer - description: City AreaGeoID (foreign key to areageo table) - CityLabel: - type: string - description: City name (resolved from areageo) - Country: - type: string - maxLength: 10 - description: Country ISO 3-letter code (e.g., IDN, USA) - CountryLabel: - type: string - description: Country name (resolved from valueset) - Race: - type: string - maxLength: 100 - MaritalStatus: - type: string - enum: [A, B, D, M, S, W] - description: 'A: Annulled, B: Separated, D: Divorced, M: Married, S: Single, W: Widowed' - Religion: - type: string - maxLength: 100 - Ethnic: - type: string - maxLength: 100 - - PatientListResponse: - type: object - properties: - status: - type: string - example: success - data: - type: array - items: - $ref: '#/components/schemas/Patient' - pagination: - type: object - properties: - page: - type: integer - perPage: - type: integer - total: - type: integer - - # Patient Visit - PatientVisit: - type: object - properties: - InternalPVID: - type: integer - description: Primary key (auto-generated) - PVID: - type: string - description: Visit ID (auto-generated with DV prefix if not provided) - InternalPID: - type: integer - description: Reference to patient - EpisodeID: - type: string - description: Episode identifier - SiteID: - type: integer - description: Site reference - CreateDate: - type: string - format: date-time - EndDate: - type: string - format: date-time - ArchivedDate: - type: string - format: date-time - DelDate: - type: string - format: date-time - PatDiag: - type: object - description: Diagnosis information (optional) - properties: - DiagCode: - type: string - Diagnosis: - type: string - PatVisitADT: - type: object - description: ADT (Admission/Discharge/Transfer) information (optional) - properties: - ADTCode: - type: string - enum: [A01, A02, A03, A04, A08] - LocationID: - type: integer - AttDoc: - type: integer - description: Attending physician ContactID - RefDoc: - type: integer - description: Referring physician ContactID - AdmDoc: - type: integer - description: Admitting physician ContactID - CnsDoc: - type: integer - description: Consulting physician ContactID - - # PatVisitADT (for standalone ADT operations) - PatVisitADT: - type: object - properties: - PVADTID: - type: integer - description: Primary key (auto-generated) - InternalPVID: - type: integer - description: Reference to patient visit - ADTCode: - type: string - enum: [A01, A02, A03, A04, A08] - description: | - A01: Admit - A02: Transfer - A03: Discharge - A04: Register - A08: Update - LocationID: - type: integer - description: Location/ward reference - AttDoc: - type: integer - description: Attending physician ContactID - RefDoc: - type: integer - description: Referring physician ContactID - AdmDoc: - type: integer - description: Admitting physician ContactID - CnsDoc: - type: integer - description: Consulting physician ContactID - CreateDate: - type: string - format: date-time - EndDate: - type: string - format: date-time - ArchivedDate: - type: string - format: date-time - DelDate: - type: string - format: date-time - - # Organization - Account: - type: object - properties: - id: - type: integer - AccountName: - type: string - AccountCode: - type: string - AccountType: - type: string - - Site: - type: object - properties: - id: - type: integer - SiteName: - type: string - SiteCode: - type: string - AccountID: - type: integer - - Discipline: - type: object - properties: - id: - type: integer - DisciplineName: - type: string - DisciplineCode: - type: string - - Department: - type: object - properties: - id: - type: integer - DeptName: - type: string - DeptCode: - type: string - SiteID: - type: integer - - Workstation: - type: object - properties: - id: - type: integer - WorkstationName: - type: string - WorkstationCode: - type: string - SiteID: - type: integer - DepartmentID: - type: integer - - # Specimen - Specimen: - type: object - properties: - id: - type: integer - SpecimenID: - type: string - PatientID: - type: string - SpecimenType: - type: string - description: Specimen type code - SpecimenTypeLabel: - type: string - description: Specimen type display text - CollectionDate: - type: string - format: date-time - CollectionMethod: - type: string - description: Collection method code - CollectionMethodLabel: - type: string - description: Collection method display text - ContainerID: - type: integer - SpecimenStatus: - type: string - description: Specimen status code - SpecimenStatusLabel: - type: string - description: Specimen status display text - BodySite: - type: string - description: Body site code - BodySiteLabel: - type: string - description: Body site display text - - ContainerDef: - type: object - properties: - id: - type: integer - ContainerCode: - type: string - ContainerName: - type: string - ConCategory: - type: string - description: Container category code - ConCategoryLabel: - type: string - description: Container category display text - ConSize: - type: string - description: Container size code - ConSizeLabel: - type: string - description: Container size display text - CapColor: - type: string - description: Cap color code - CapColorLabel: - type: string - description: Cap color display text - - SpecimenPrep: - type: object - properties: - id: - type: integer - PrepCode: - type: string - PrepName: - type: string - Description: - type: string - - SpecimenStatus: - type: object - properties: - id: - type: integer - StatusCode: - type: string - StatusName: - type: string - Description: - type: string - Status: - type: string - description: Status code - StatusLabel: - type: string - description: Status display text - Activity: - type: string - description: Activity code - ActivityLabel: - type: string - description: Activity display text - - SpecimenCollection: - type: object - properties: - id: - type: integer - CollectionCode: - type: string - CollectionName: - type: string - Description: - type: string - CollectionMethod: - type: string - description: Collection method code - CollectionMethodLabel: - type: string - description: Collection method display text - Additive: - type: string - description: Additive code - AdditiveLabel: - type: string - description: Additive display text - SpecimenRole: - type: string - description: Specimen role code - SpecimenRoleLabel: - type: string - description: Specimen role display text - - # Tests - TestDefinition: - type: object - properties: - id: - type: integer - TestCode: - type: string - TestName: - type: string - TestType: - type: string - enum: [TEST, PARAM, CALC, GROUP, TITLE] - description: | - TEST: Technical test - PARAM: Parameter - CALC: Calculated - GROUP: Panel/Profile - TITLE: Section header - DisciplineID: - type: integer - DisciplineName: - type: string - DepartmentID: - type: integer - DepartmentName: - type: string - Unit: - type: string - Formula: - type: string - refnum: - type: array - description: Numeric reference ranges (optional). Mutually exclusive with reftxt - a test can only have ONE reference type. - items: - type: object - properties: - RefNumID: - type: integer - NumRefType: - type: string - enum: [NMRC, THOLD] - description: NMRC=Numeric range, THOLD=Threshold - NumRefTypeLabel: - type: string - RangeType: - type: string - RangeTypeLabel: - type: string - Sex: - type: string - SexLabel: - type: string - LowSign: - type: string - LowSignLabel: - type: string - HighSign: - type: string - HighSignLabel: - type: string - High: - type: number - format: float - Low: - type: number - format: float - AgeStart: - type: integer - AgeEnd: - type: integer - Flag: - type: string - Interpretation: - type: string - reftxt: - type: array - description: Text reference ranges (optional). Mutually exclusive with refnum - a test can only have ONE reference type. - items: - type: object - properties: - RefTxtID: - type: integer - TxtRefType: - type: string - enum: [TEXT, VSET] - description: TEXT=Free text, VSET=Value set - TxtRefTypeLabel: - type: string - Sex: - type: string - SexLabel: - type: string - AgeStart: - type: integer - AgeEnd: - type: integer - RefTxt: - type: string - Flag: - type: string - examples: - $1: - Unit: mg/dL - refnum: - - RefNumID: 1 - NumRefType: NMRC - NumRefTypeLabel: Numeric - RangeType: REF - RangeTypeLabel: Reference Range - Sex: '2' - SexLabel: Male - LowSign: GE - LowSignLabel: ">=" - HighSign: LE - HighSignLabel: "<=" - Low: 70 - High: 100 - AgeStart: 18 - AgeEnd: 99 - Flag: N - Interpretation: Normal - TEST_numeric_thold: - summary: Technical test - threshold reference (THOLD) - value: - id: 1 - TestCode: GLU - TestName: Glucose - TestType: TEST - DisciplineID: 1 - DepartmentID: 1 - Unit: mg/dL - refnum: - - RefNumID: 2 - NumRefType: THOLD - NumRefTypeLabel: Threshold - RangeType: PANIC - RangeTypeLabel: Panic Range - Sex: '1' - SexLabel: Female - LowSign: LT - LowSignLabel: "<" - High: 40 - AgeStart: 0 - AgeEnd: 120 - Flag: L - Interpretation: Critical Low - $2: - Unit: null - reftxt: - - RefTxtID: 1 - TxtRefType: TEXT - TxtRefTypeLabel: Text - Sex: '2' - SexLabel: Male - AgeStart: 18 - AgeEnd: 99 - RefTxt: 'NORM=Normal;HYPO=Hypochromic;MACRO=Macrocytic' - Flag: N - TEST_text_vset: - summary: Technical test - text reference (VSET) - value: - id: 1 - TestCode: STAGE - TestName: Disease Stage - TestType: TEST - DisciplineID: 1 - DepartmentID: 1 - Unit: null - reftxt: - - RefTxtID: 2 - TxtRefType: VSET - TxtRefTypeLabel: Value Set - Sex: '1' - SexLabel: Female - AgeStart: 0 - AgeEnd: 120 - RefTxt: 'STG1=Stage 1;STG2=Stage 2;STG3=Stage 3;STG4=Stage 4' - Flag: N - PARAM: - summary: Parameter - no reference range allowed - value: - id: 2 - TestCode: GLU_FAST - TestName: Fasting Glucose - TestType: PARAM - DisciplineID: 1 - DepartmentID: 1 - Unit: mg/dL - $3: - Unit: null - Formula: "BUN / Creatinine" - refnum: - - RefNumID: 5 - NumRefType: NMRC - NumRefTypeLabel: Numeric - RangeType: REF - RangeTypeLabel: Reference Range - Sex: '1' - SexLabel: Female - LowSign: GE - LowSignLabel: ">=" - HighSign: LE - HighSignLabel: "<=" - Low: 10 - High: 20 - AgeStart: 18 - AgeEnd: 120 - Flag: N - Interpretation: Normal - $4: - Unit: null - Formula: "BUN / Creatinine" - refnum: - - RefNumID: 6 - NumRefType: THOLD - NumRefTypeLabel: Threshold - RangeType: PANIC - RangeTypeLabel: Panic Range - Sex: '1' - SexLabel: Female - LowSign: GT - LowSignLabel: ">" - Low: 20 - AgeStart: 18 - AgeEnd: 120 - Flag: H - Interpretation: Elevated - possible prerenal cause - - GROUP: - summary: Panel/Profile - no reference range allowed - value: - id: 4 - TestCode: LIPID - TestName: Lipid Panel - TestType: GROUP - DisciplineID: 1 - DepartmentID: 1 - Unit: null - TITLE: - summary: Section header - no reference range allowed - value: - id: 5 - TestCode: CHEM_HEADER - TestName: '--- CHEMISTRY ---' - TestType: TITLE - DisciplineID: 1 - DepartmentID: 1 - Unit: null - - TestMap: - type: object - properties: - id: - type: integer - TestMapID: - type: integer - TestCode: - type: string - HostCode: - type: string - HostName: - type: string - ClientCode: - type: string - ClientName: - type: string - HostType: - type: string - description: Host type code - HostTypeLabel: - type: string - description: Host type display text - ClientType: - type: string - description: Client type code - ClientTypeLabel: - type: string - description: Client type display text - - # Orders - OrderTest: - type: object - properties: - OrderID: - type: string - PatientID: - type: string - VisitID: - type: string - OrderDate: - type: string - format: date-time - OrderStatus: - type: string - enum: [ORD, SCH, ANA, VER, REV, REP] - description: | - ORD: Ordered - SCH: Scheduled - ANA: Analysis - VER: Verified - REV: Reviewed - REP: Reported - OrderStatusLabel: - type: string - description: Order status display text - Priority: - type: string - enum: [R, S, U] - description: | - R: Routine - S: Stat - U: Urgent - PriorityLabel: - type: string - description: Priority display text - SiteID: - type: integer - RequestingPhysician: - type: string - - OrderItem: - type: object - properties: - id: - type: integer - OrderID: - type: string - TestID: - type: integer - SpecimenID: - type: string - Status: - type: string - - # Edge API - EdgeResultRequest: - type: object - required: - - sample_id - - instrument_id - properties: - sample_id: - type: string - description: Sample barcode/identifier - instrument_id: - type: string - description: Instrument identifier - patient_id: - type: string - description: Patient identifier (optional) - results: - type: array - items: - type: object - properties: - test_code: - type: string - result_value: - type: string - unit: - type: string - flags: - type: string - enum: [H, L, N, A] - description: H=High, L=Low, N=Normal, A=Abnormal - - EdgeResultResponse: - type: object - properties: - status: - type: string - example: success - message: - type: string - example: Result received and queued - data: - type: object - properties: - edge_res_id: - type: integer - sample_id: - type: string - instrument_id: - type: string - - EdgeOrder: - type: object - properties: - OrderID: - type: string - PatientID: - type: string - SampleID: - type: string - Tests: - type: array - items: - type: object - properties: - TestCode: - type: string - TestName: - type: string - SpecimenType: - type: string - Priority: - type: string - DueDateTime: - type: string - format: date-time - - # ValueSets - ValueSetLibItem: - type: object - description: Library/system value set item from JSON files - properties: - value: - type: string - description: The value/key code - label: - type: string - description: The display label - - ValueSetDef: - type: object - description: User-defined value set definition (from database) - properties: - VSetID: - type: integer - description: Primary key - SiteID: - type: integer - description: Site reference - VSName: - type: string - description: Value set name - VSDesc: - type: string - description: Value set description - CreateDate: - type: string - format: date-time - description: Creation timestamp - EndDate: - type: string - format: date-time - nullable: true - description: Soft delete timestamp - ItemCount: - type: integer - description: Number of items in this value set - - ValueSetItem: - type: object - description: User-defined value set item (from database) - properties: - VID: - type: integer - description: Primary key - SiteID: - type: integer - description: Site reference - VSetID: - type: integer - description: Reference to value set definition - VOrder: - type: integer - description: Display order - VValue: - type: string - description: The value code - VDesc: - type: string - description: The display description/label - VCategory: - type: string - description: Category code - CreateDate: - type: string - format: date-time - description: Creation timestamp - EndDate: - type: string - format: date-time - nullable: true - description: Soft delete timestamp - VSName: - type: string - description: Value set name (from joined definition) - - # Master Data - Location: - type: object - properties: - LocationID: - type: integer - description: Primary key - SiteID: - type: integer - description: Reference to site - LocCode: - type: string - maxLength: 6 - description: Location code (short identifier) - Parent: - type: integer - nullable: true - description: Parent location ID for hierarchical locations - LocFull: - type: string - maxLength: 255 - description: Full location name - Description: - type: string - maxLength: 255 - description: Location description - LocType: - type: string - description: Location type code (e.g., ROOM, WARD, BUILDING) - CreateDate: - type: string - format: date-time - EndDate: - type: string - format: date-time - nullable: true - - Contact: - type: object - properties: - ContactID: - type: integer - description: Primary key - NameFirst: - type: string - description: First name (required) - NameLast: - type: string - description: Last name - Title: - type: string - description: Title (e.g., Dr, Mr, Mrs) - Initial: - type: string - description: Middle initial - Birthdate: - type: string - format: date-time - description: Date of birth - EmailAddress1: - type: string - format: email - description: Primary email address - EmailAddress2: - type: string - format: email - description: Secondary email address - Phone: - type: string - description: Primary phone number - MobilePhone1: - type: string - description: Primary mobile number - MobilePhone2: - type: string - description: Secondary mobile number - Specialty: - type: string - description: Medical specialty code - SubSpecialty: - type: string - description: Sub-specialty code - CreateDate: - type: string - format: date-time - EndDate: - type: string - format: date-time - description: Occupation display text - - Occupation: - type: object - properties: - OccupationID: - type: integer - description: Primary key - OccCode: - type: string - description: Occupation code - OccText: - type: string - description: Occupation name/text - Description: - type: string - description: Additional description - CreateDate: - type: string - format: date-time - - MedicalSpecialty: - type: object - properties: - SpecialtyID: - type: integer - description: Primary key - SpecialtyText: - type: string - description: Specialty name/text - Parent: - type: integer - description: Parent specialty ID for hierarchical structure - Title: - type: string - description: Title/abbreviation - CreateDate: - type: string - format: date-time - EndDate: - type: string - format: date-time - - Counter: - type: object - properties: - CounterID: - type: integer - description: Primary key - CounterDesc: - type: string - description: Counter description/name - CounterValue: - type: integer - description: Current counter value - CounterStart: - type: integer - description: Starting value for the counter - CounterEnd: - type: integer - description: Ending value (for auto-reset) - CounterReset: - type: string - description: Reset pattern (e.g., D=Daily, M=Monthly, Y=Yearly) - CreateDate: - type: string - format: date-time - EndDate: - type: string - format: date-time - - # Dashboard + $ref: './components/schemas/common.yaml#/ErrorResponse' DashboardSummary: - type: object - properties: - pendingOrders: - type: integer - todayResults: - type: integer - criticalResults: - type: integer - activePatients: - type: integer - -paths: - # ======================================== - # Authentication Routes - # ======================================== - /api/auth/login: - post: - tags: [Authentication] - summary: User login - description: Authenticate user and receive JWT token via HTTP-only cookie - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/LoginRequest' - application/x-www-form-urlencoded: - schema: - $ref: '#/components/schemas/LoginRequest' - responses: - '200': - description: Login successful - headers: - Set-Cookie: - description: JWT token in HTTP-only cookie - schema: - type: string - content: - application/json: - schema: - $ref: '#/components/schemas/LoginResponse' - '400': - description: Missing username - content: - application/json: - schema: - $ref: '#/components/schemas/ErrorResponse' - '401': - description: Invalid credentials - content: - application/json: - schema: - $ref: '#/components/schemas/ErrorResponse' - - /api/auth/logout: - post: - tags: [Authentication] - summary: User logout - description: Clear JWT token cookie - security: - - bearerAuth: [] - responses: - '200': - description: Logout successful - content: - application/json: - schema: - $ref: '#/components/schemas/SuccessResponse' - - /api/auth/check: - get: - tags: [Authentication] - summary: Check authentication status - security: - - bearerAuth: [] - - cookieAuth: [] - responses: - '200': - description: Authenticated - content: - application/json: - schema: - type: object - properties: - authenticated: - type: boolean - user: - type: object - '401': - description: Not authenticated - - /api/auth/register: - post: - tags: [Authentication] - summary: Register new user - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/RegisterRequest' - responses: - '201': - description: User created - content: - application/json: - schema: - $ref: '#/components/schemas/SuccessResponse' - - /api/auth/change_pass: - post: - tags: [Authentication] - summary: Change password - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - current_password - - new_password - properties: - current_password: - type: string - format: password - new_password: - type: string - format: password - responses: - '200': - description: Password changed successfully - - # ======================================== - # V2 Authentication Routes - # ======================================== - /v2/auth/login: - post: - tags: [Authentication] - summary: V2 User login - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/LoginRequest' - responses: - '200': - description: Login successful - content: - application/json: - schema: - $ref: '#/components/schemas/LoginResponse' - - /v2/auth/logout: - post: - tags: [Authentication] - summary: V2 User logout - responses: - '200': - description: Logout successful - - /v2/auth/check: - get: - tags: [Authentication] - summary: V2 Check authentication - responses: - '200': - description: Auth check result - - /v2/auth/register: - post: - tags: [Authentication] - summary: V2 Register new user - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/RegisterRequest' - responses: - '201': - description: User created - - # ======================================== - # Patient Routes - # ======================================== - /api/patient: - get: - tags: [Patients] - summary: List patients - security: - - bearerAuth: [] - parameters: - - name: page - in: query - schema: - type: integer - default: 1 - - name: perPage - in: query - schema: - type: integer - default: 20 - - name: InternalPID - in: query - schema: - type: integer - description: Filter by internal patient ID - - name: PatientID - in: query - schema: - type: string - description: Filter by patient ID - - name: Name - in: query - schema: - type: string - description: Search by patient name - - name: Birthdate - in: query - schema: - type: string - format: date - description: Filter by birthdate (YYYY-MM-DD) - responses: - '200': - description: List of patients - content: - application/json: - schema: - $ref: '#/components/schemas/PatientListResponse' - - post: - tags: [Patients] - summary: Create new patient - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/Patient' - responses: - '201': - description: Patient created successfully - content: - application/json: - schema: - $ref: '#/components/schemas/SuccessResponse' - '422': - description: Validation error - content: - application/json: - schema: - $ref: '#/components/schemas/ErrorResponse' - - patch: - tags: [Patients] - summary: Update patient - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/Patient' - responses: - '200': - description: Patient updated successfully - - delete: - tags: [Patients] - summary: Delete patient (soft delete) - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - InternalPID - properties: - InternalPID: - type: integer - description: Internal patient record ID - responses: - '200': - description: Patient deleted successfully - - /api/patient/check: - get: - tags: [Patients] - summary: Check if patient exists - security: - - bearerAuth: [] - parameters: - - name: PatientID - in: query - schema: - type: string - description: Patient ID to check - - name: EmailAddress1 - in: query - schema: - type: string - format: email - description: Email address to check - responses: - '200': - description: Patient check result - content: - application/json: - schema: - type: object - properties: - exists: - type: boolean - data: - $ref: '#/components/schemas/Patient' - - /api/patient/{id}: - get: - tags: [Patients] - summary: Get patient by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - description: Internal patient record ID - responses: - '200': - description: Patient details - content: - application/json: - schema: - type: object - properties: - status: - type: string - data: - $ref: '#/components/schemas/Patient' - - # ======================================== - # Patient Visit Routes - # ======================================== - /api/patvisit: - get: - tags: [Patient Visits] - summary: List patient visits - security: - - bearerAuth: [] - parameters: - - name: page - in: query - schema: - type: integer - - name: perPage - in: query - schema: - type: integer - responses: - '200': - description: List of patient visits - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - type: array - items: - $ref: '#/components/schemas/PatientVisit' - total: - type: integer - description: Total number of records - page: - type: integer - description: Current page number - per_page: - type: integer - description: Number of records per page - - post: - tags: [Patient Visits] - summary: Create patient visit - description: | - Creates a new patient visit. PVID is auto-generated with 'DV' prefix if not provided. - Can optionally include PatDiag (diagnosis) and PatVisitADT (ADT information). - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - InternalPID - properties: - PVID: - type: string - description: Visit ID (auto-generated with DV prefix if not provided) - InternalPID: - type: integer - description: Patient ID (required) - EpisodeID: - type: string - description: Episode identifier - SiteID: - type: integer - description: Site reference - PatDiag: - type: object - description: Optional diagnosis information - properties: - DiagCode: - type: string - Diagnosis: - type: string - PatVisitADT: - type: object - description: Optional ADT information - properties: - ADTCode: - type: string - enum: [A01, A02, A03, A04, A08] - LocationID: - type: integer - AttDoc: - type: integer - RefDoc: - type: integer - AdmDoc: - type: integer - CnsDoc: - type: integer - responses: - '201': - description: Visit created successfully - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - type: object - properties: - PVID: - type: string - InternalPVID: - type: integer - - patch: - tags: [Patient Visits] - summary: Update patient visit - description: | - Updates an existing patient visit. InternalPVID is required. - Can update main visit data, PatDiag, and add new PatVisitADT records. - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - InternalPVID - properties: - InternalPVID: - type: integer - description: Visit ID (required) - PVID: - type: string - InternalPID: - type: integer - EpisodeID: - type: string - SiteID: - type: integer - PatDiag: - type: object - description: Diagnosis information (will update if exists) - properties: - DiagCode: - type: string - Diagnosis: - type: string - PatVisitADT: - type: array - description: Array of ADT records to add (new records only) - items: - type: object - properties: - ADTCode: - type: string - enum: [A01, A02, A03, A04, A08] - LocationID: - type: integer - AttDoc: - type: integer - RefDoc: - type: integer - AdmDoc: - type: integer - CnsDoc: - type: integer - sequence: - type: integer - description: Used for ordering multiple ADT records - responses: - '200': - description: Visit updated successfully - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - type: object - properties: - PVID: - type: string - InternalPVID: - type: integer - - delete: - tags: [Patient Visits] - summary: Delete patient visit - security: - - bearerAuth: [] - responses: - '200': - description: Visit deleted successfully - - /api/patvisit/{id}: - get: - tags: [Patient Visits] - summary: Get visit by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: string - description: PVID (visit identifier like DV00001) - responses: - '200': - description: Visit details - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - $ref: '#/components/schemas/PatientVisit' - - /api/patvisit/patient/{patientId}: - get: - tags: [Patient Visits] - summary: Get visits by patient ID - security: - - bearerAuth: [] - parameters: - - name: patientId - in: path - required: true - schema: - type: integer - description: Internal Patient ID (InternalPID) - responses: - '200': - description: Patient visits list - content: - application/json: - schema: - type: object - properties: - status: - type: string - data: - type: array - items: - $ref: '#/components/schemas/PatientVisit' - - /api/patvisitadt: - post: - tags: [Patient Visits] - summary: Create ADT record - description: Create a new Admission/Discharge/Transfer record - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/PatVisitADT' - responses: - '201': - description: ADT record created successfully - content: - application/json: - schema: - $ref: '#/components/schemas/SuccessResponse' - - patch: - tags: [Patient Visits] - summary: Update ADT record - description: Update an existing ADT record - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/PatVisitADT' - responses: - '200': - description: ADT record updated successfully - content: - application/json: - schema: - $ref: '#/components/schemas/SuccessResponse' - - delete: - tags: [Patient Visits] - summary: Delete ADT visit (soft delete) - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - PVADTID - properties: - PVADTID: - type: integer - description: ADT record ID to delete - responses: - '200': - description: ADT visit deleted successfully - - /api/patvisitadt/visit/{visitId}: - get: - tags: [Patient Visits] - summary: Get ADT history by visit ID - description: Retrieve the complete Admission/Discharge/Transfer history for a visit, including all locations and doctors - security: - - bearerAuth: [] - parameters: - - name: visitId - in: path - required: true - schema: - type: integer - description: Internal Visit ID (InternalPVID) - responses: - '200': - description: ADT history retrieved successfully - content: - application/json: - schema: - type: object - properties: - status: - type: string - example: success - message: - type: string - example: ADT history retrieved - data: - type: array - items: - type: object - properties: - PVADTID: - type: integer - InternalPVID: - type: integer - ADTCode: - type: string - enum: [A01, A02, A03, A04, A08] - LocationID: - type: integer - LocationName: - type: string - AttDoc: - type: integer - AttDocFirstName: - type: string - AttDocLastName: - type: string - RefDoc: - type: integer - RefDocFirstName: - type: string - RefDocLastName: - type: string - AdmDoc: - type: integer - AdmDocFirstName: - type: string - AdmDocLastName: - type: string - CnsDoc: - type: integer - CnsDocFirstName: - type: string - CnsDocLastName: - type: string - CreateDate: - type: string - format: date-time - EndDate: - type: string - format: date-time - delete: - tags: [Patient Visits] - summary: Delete ADT visit (soft delete) - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - PVADTID - properties: - PVADTID: - type: integer - description: ADT record ID to delete - responses: - '200': - description: ADT visit deleted successfully - - /api/patvisitadt/{id}: - get: - tags: [Patient Visits] - summary: Get ADT record by ID - description: Retrieve a single ADT record by its ID, including location and doctor details - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - description: ADT record ID (PVADTID) - responses: - '200': - description: ADT record retrieved successfully - content: - application/json: - schema: - type: object - properties: - status: - type: string - example: success - message: - type: string - example: ADT record retrieved - data: - type: object - properties: - PVADTID: - type: integer - InternalPVID: - type: integer - ADTCode: - type: string - enum: [A01, A02, A03, A04, A08] - LocationID: - type: integer - LocationName: - type: string - AttDoc: - type: integer - AttDocFirstName: - type: string - AttDocLastName: - type: string - RefDoc: - type: integer - RefDocFirstName: - type: string - RefDocLastName: - type: string - AdmDoc: - type: integer - AdmDocFirstName: - type: string - AdmDocLastName: - type: string - CnsDoc: - type: integer - CnsDocFirstName: - type: string - CnsDocLastName: - type: string - CreateDate: - type: string - format: date-time - EndDate: - type: string - format: date-time - - /api/organization/account/{id}: - get: - tags: [Organization] - summary: Get account by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Account details - content: - application/json: - schema: - $ref: '#/components/schemas/Account' - - # ======================================== - # Organization - Site Routes - # ======================================== - /api/organization/site: - get: - tags: [Organization] - summary: List sites - security: - - bearerAuth: [] - responses: - '200': - description: List of sites - - post: - tags: [Organization] - summary: Create site - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/Site' - responses: - '201': - description: Site created - - patch: - tags: [Organization] - summary: Update site - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - id - properties: - id: - type: integer - SiteName: - type: string - SiteCode: - type: string - AccountID: - type: integer - responses: - '200': - description: Site updated - - delete: - tags: [Organization] - summary: Delete site - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - id - properties: - id: - type: integer - responses: - '200': - description: Site deleted - - /api/organization/site/{id}: - get: - tags: [Organization] - summary: Get site by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Site details - - # ======================================== - # Organization - Discipline Routes - # ======================================== - /api/organization/discipline: - get: - tags: [Organization] - summary: List disciplines - security: - - bearerAuth: [] - responses: - '200': - description: List of disciplines - - post: - tags: [Organization] - summary: Create discipline - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/Discipline' - responses: - '201': - description: Discipline created - - patch: - tags: [Organization] - summary: Update discipline - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - id - properties: - id: - type: integer - DisciplineName: - type: string - DisciplineCode: - type: string - responses: - '200': - description: Discipline updated - - delete: - tags: [Organization] - summary: Delete discipline - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - id - properties: - id: - type: integer - responses: - '200': - description: Discipline deleted - - /api/organization/discipline/{id}: - get: - tags: [Organization] - summary: Get discipline by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Discipline details - - # ======================================== - # Organization - Department Routes - # ======================================== - /api/organization/department: - get: - tags: [Organization] - summary: List departments - security: - - bearerAuth: [] - responses: - '200': - description: List of departments - - post: - tags: [Organization] - summary: Create department - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/Department' - responses: - '201': - description: Department created - - patch: - tags: [Organization] - summary: Update department - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - id - properties: - id: - type: integer - DeptName: - type: string - DeptCode: - type: string - SiteID: - type: integer - responses: - '200': - description: Department updated - - delete: - tags: [Organization] - summary: Delete department - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - id - properties: - id: - type: integer - responses: - '200': - description: Department deleted - - /api/organization/department/{id}: - get: - tags: [Organization] - summary: Get department by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Department details - - # ======================================== - # Organization - Workstation Routes - # ======================================== - /api/organization/workstation: - get: - tags: [Organization] - summary: List workstations - security: - - bearerAuth: [] - responses: - '200': - description: List of workstations - - post: - tags: [Organization] - summary: Create workstation - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/Workstation' - responses: - '201': - description: Workstation created - - patch: - tags: [Organization] - summary: Update workstation - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - id - properties: - id: - type: integer - WorkstationName: - type: string - WorkstationCode: - type: string - SiteID: - type: integer - DepartmentID: - type: integer - responses: - '200': - description: Workstation updated - - delete: - tags: [Organization] - summary: Delete workstation - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - id - properties: - id: - type: integer - responses: - '200': - description: Workstation deleted - - /api/organization/workstation/{id}: - get: - tags: [Organization] - summary: Get workstation by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Workstation details - - # ======================================== - # Specimen Routes - # ======================================== - /api/specimen: - get: - tags: [Specimen] - summary: List specimens - security: - - bearerAuth: [] - responses: - '200': - description: List of specimens - - post: - tags: [Specimen] - summary: Create specimen - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/Specimen' - responses: - '201': - description: Specimen created - - patch: - tags: [Specimen] - summary: Update specimen - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/Specimen' - responses: - '200': - description: Specimen updated - - /api/specimen/{id}: - get: - tags: [Specimen] - summary: Get specimen by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Specimen details - - /api/specimen/container: - get: - tags: [Specimen] - summary: List container definitions - security: - - bearerAuth: [] - responses: - '200': - description: List of container definitions - - post: - tags: [Specimen] - summary: Create container definition - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/ContainerDef' - responses: - '201': - description: Container definition created - - patch: - tags: [Specimen] - summary: Update container definition - security: - - bearerAuth: [] - responses: - '200': - description: Container definition updated - - /api/specimen/container/{id}: - get: - tags: [Specimen] - summary: Get container definition by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Container definition details - - # ContainerDef aliases (same as /api/specimen/container) - /api/specimen/containerdef: - get: - tags: [Specimen] - summary: List container definitions (alias) - security: - - bearerAuth: [] - responses: - '200': - description: List of container definitions - - post: - tags: [Specimen] - summary: Create container definition (alias) - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/ContainerDef' - responses: - '201': - description: Container definition created - - patch: - tags: [Specimen] - summary: Update container definition (alias) - security: - - bearerAuth: [] - responses: - '200': - description: Container definition updated - - /api/specimen/prep: - get: - tags: [Specimen] - summary: List specimen preparations - security: - - bearerAuth: [] - responses: - '200': - description: List of specimen preparations - - post: - tags: [Specimen] - summary: Create specimen preparation - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/SpecimenPrep' - responses: - '201': - description: Specimen preparation created - - patch: - tags: [Specimen] - summary: Update specimen preparation - security: - - bearerAuth: [] - responses: - '200': - description: Specimen preparation updated - - /api/specimen/prep/{id}: - get: - tags: [Specimen] - summary: Get specimen preparation by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Specimen preparation details - - /api/specimen/status: - get: - tags: [Specimen] - summary: List specimen statuses - security: - - bearerAuth: [] - responses: - '200': - description: List of specimen statuses - - post: - tags: [Specimen] - summary: Create specimen status - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/SpecimenStatus' - responses: - '201': - description: Specimen status created - - patch: - tags: [Specimen] - summary: Update specimen status - security: - - bearerAuth: [] - responses: - '200': - description: Specimen status updated - - /api/specimen/status/{id}: - get: - tags: [Specimen] - summary: Get specimen status by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Specimen status details - - /api/specimen/collection: - get: - tags: [Specimen] - summary: List specimen collection methods - security: - - bearerAuth: [] - responses: - '200': - description: List of collection methods - - post: - tags: [Specimen] - summary: Create specimen collection method - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/SpecimenCollection' - responses: - '201': - description: Collection method created - - patch: - tags: [Specimen] - summary: Update specimen collection method - security: - - bearerAuth: [] - responses: - '200': - description: Collection method updated - - /api/specimen/collection/{id}: - get: - tags: [Specimen] - summary: Get specimen collection method by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Collection method details - - # ======================================== - # Tests Routes - # ======================================== - /api/tests: - get: - tags: [Tests] - summary: List test definitions - security: - - bearerAuth: [] - parameters: - - name: page - in: query - schema: - type: integer - - name: perPage - in: query - schema: - type: integer - - name: SiteID - in: query - schema: - type: integer - description: Filter by site ID - - name: TestType - in: query - schema: - type: string - enum: [TEST, PARAM, CALC, GROUP, TITLE] - description: Filter by test type - - name: VisibleScr - in: query - schema: - type: integer - enum: [0, 1] - description: Filter by screen visibility (0=hidden, 1=visible) - - name: VisibleRpt - in: query - schema: - type: integer - enum: [0, 1] - description: Filter by report visibility (0=hidden, 1=visible) - - name: TestSiteName - in: query - schema: - type: string - description: Search by test name or code - responses: - '200': - description: List of test definitions - content: - application/json: - schema: - type: object - properties: - status: - type: string - data: - type: array - items: - $ref: '#/components/schemas/TestDefinition' - - post: - tags: [Tests] - summary: Create test definition - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/TestDefinition' - responses: - '201': - description: Test definition created - - patch: - tags: [Tests] - summary: Update test definition - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/TestDefinition' - responses: - '200': - description: Test definition updated - - /api/tests/{id}: - get: - tags: [Tests] - summary: Get test definition by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: Test definition details - - # ======================================== - # Orders Routes - # ======================================== - /api/ordertest: - get: - tags: [Orders] - summary: List orders - security: - - bearerAuth: [] - parameters: - - name: page - in: query - schema: - type: integer - - name: perPage - in: query - schema: - type: integer - - name: InternalPID - in: query - schema: - type: integer - description: Filter by internal patient ID - - name: OrderStatus - in: query - schema: - type: string - enum: [ORD, SCH, ANA, VER, REV, REP] - description: | - ORD: Ordered - SCH: Scheduled - ANA: Analysis - VER: Verified - REV: Reviewed - REP: Reported - responses: - '200': - description: List of orders - - post: - tags: [Orders] - summary: Create order - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - PatientID - - Tests - properties: - PatientID: - type: string - VisitID: - type: string - Priority: - type: string - enum: [R, S, U] - description: | - R: Routine - S: Stat - U: Urgent - SiteID: - type: integer - RequestingPhysician: - type: string - Tests: - type: array - items: - type: object - properties: - TestID: - type: integer - SpecimenType: - type: string - responses: - '201': - description: Order created successfully - - patch: - tags: [Orders] - summary: Update order - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/OrderTest' - responses: - '200': - description: Order updated - - delete: - tags: [Orders] - summary: Delete order - security: - - bearerAuth: [] - responses: - '200': - description: Order deleted - - /api/ordertest/status: - post: - tags: [Orders] - summary: Update order status - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - OrderID - - OrderStatus - properties: - OrderID: - type: string - OrderStatus: - type: string - enum: [ORD, SCH, ANA, VER, REV, REP] - description: | - ORD: Ordered - SCH: Scheduled - ANA: Analysis - VER: Verified - REV: Reviewed - REP: Reported - responses: - '200': - description: Order status updated - - /api/ordertest/{id}: - get: - tags: [Orders] - summary: Get order by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: string - responses: - '200': - description: Order details - - # ======================================== - # Edge API Routes - # ======================================== - /api/edge/results: - post: - tags: [Edge API] - summary: Receive results from instrument (tiny-edge) - description: | - Receives instrument results and stores them in the edgeres table for processing. - This endpoint is typically called by the tiny-edge middleware connected to laboratory analyzers. - requestBody: - required: true - content: - application/json: - schema: - $ref: '#/components/schemas/EdgeResultRequest' - responses: - '201': - description: Result received and queued - content: - application/json: - schema: - $ref: '#/components/schemas/EdgeResultResponse' - '400': - description: Invalid JSON payload - - /api/edge/orders: - get: - tags: [Edge API] - summary: Fetch pending orders for instruments - description: Returns orders that need to be sent to laboratory instruments for testing - parameters: - - name: instrument_id - in: query - schema: - type: string - description: Filter by instrument - - name: status - in: query - schema: - type: string - enum: [pending, acknowledged] - description: Filter by status - responses: - '200': - description: List of orders - content: - application/json: - schema: - type: object - properties: - status: - type: string - data: - type: array - items: - $ref: '#/components/schemas/EdgeOrder' - - /api/edge/orders/{orderId}/ack: - post: - tags: [Edge API] - summary: Acknowledge order delivery - description: Mark order as acknowledged by the instrument - parameters: - - name: orderId - in: path - required: true - schema: - type: integer - description: Edge order ID - responses: - '200': - description: Order acknowledged - content: - application/json: - schema: - $ref: '#/components/schemas/SuccessResponse' - - /api/edge/status: - post: - tags: [Edge API] - summary: Log instrument status update - description: Receive status updates from laboratory instruments - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - instrument_id - - status - properties: - instrument_id: - type: string - status: - type: string - enum: [online, offline, error, maintenance] - message: - type: string - timestamp: - type: string - format: date-time - responses: - '200': - description: Status logged - - # ======================================== - # ValueSet Routes - # ======================================== - /api/valueset: - get: - tags: [ValueSets] - summary: List lib value sets - description: List all library/system value sets from JSON files with item counts. Returns an object where keys are value set names and values are item counts. - security: - - bearerAuth: [] - parameters: - - name: search - in: query - schema: - type: string - description: Optional search term to filter value set names - responses: - '200': - description: List of lib value sets with item counts - content: - application/json: - schema: - type: object - properties: - status: - type: string - example: success - data: - type: object - additionalProperties: - type: integer - description: Number of items in each value set - example: - sex: 3 - marital_status: 6 - order_status: 6 - - /api/valueset/{key}: - get: - tags: [ValueSets] - summary: Get lib value set by key - description: | - Get a specific library/system value set from JSON files. - - **Available value set keys:** - - `activity_result` - Activity Result - - `additive` - Additive - - `adt_event` - ADT Event - - `area_class` - Area Class - - `body_site` - Body Site - - `collection_method` - Collection Method - - `container_cap_color` - Container Cap Color - - `container_class` - Container Class - - `container_size` - Container Size - - `country` - Country - - `death_indicator` - Death Indicator - - `did_type` - DID Type - - `enable_disable` - Enable/Disable - - `entity_type` - Entity Type - - `ethnic` - Ethnic - - `fasting_status` - Fasting Status - - `formula_language` - Formula Language - - `generate_by` - Generate By - - `identifier_type` - Identifier Type - - `location_type` - Location Type - - `marital_status` - Marital Status - - `math_sign` - Math Sign - - `numeric_ref_type` - Numeric Reference Type - - `operation` - Operation (CRUD) - - `order_priority` - Order Priority - - `order_status` - Order Status - - `race` - Race (Ethnicity) - - `range_type` - Range Type - - `reference_type` - Reference Type - - `religion` - Religion - - `requested_entity` - Requested Entity - - `result_type` - Result Type - - `result_unit` - Result Unit - - `sex` - Sex - - `site_class` - Site Class - - `site_type` - Site Type - - `specimen_activity` - Specimen Activity - - `specimen_condition` - Specimen Condition - - `specimen_role` - Specimen Role - - `specimen_status` - Specimen Status - - `specimen_type` - Specimen Type - - `test_activity` - Test Activity - - `test_type` - Test Type - - `text_ref_type` - Text Reference Type - - `unit` - Unit - - `v_category` - VCategory - - `ws_type` - Workstation Type - security: - - bearerAuth: [] - parameters: - - name: key - in: path - required: true - schema: - type: string - enum: [activity_result, additive, adt_event, area_class, body_site, collection_method, container_cap_color, container_class, container_size, country, death_indicator, did_type, enable_disable, entity_type, ethnic, fasting_status, formula_language, generate_by, identifier_type, location_type, marital_status, math_sign, numeric_ref_type, operation, order_priority, order_status, race, range_type, reference_type, religion, requested_entity, result_type, result_unit, sex, site_class, site_type, specimen_activity, specimen_condition, specimen_role, specimen_status, specimen_type, test_activity, test_type, text_ref_type, unit, v_category, ws_type] - description: Value set key name - responses: - '200': - description: Lib value set details - content: - application/json: - schema: - type: object - properties: - status: - type: string - data: - type: array - items: - $ref: '#/components/schemas/ValueSetLibItem' - - /api/valueset/refresh: - post: - tags: [ValueSets] - summary: Refresh lib ValueSet cache - description: Clear and reload the library/system ValueSet cache from JSON files. Call this after modifying JSON files in app/Libraries/Data/. - security: - - bearerAuth: [] - responses: - '200': - description: Lib ValueSet cache refreshed - content: - application/json: - schema: - type: object - properties: - status: - type: string - example: success - message: - type: string - example: Cache cleared - - /api/valueset/user/items: - get: - tags: [ValueSets] - summary: List user value set items - description: List value set items from database (user-defined) - security: - - bearerAuth: [] - parameters: - - name: VSetID - in: query - schema: - type: integer - description: Filter by ValueSet ID - - name: search - in: query - schema: - type: string - description: Search term to filter by VValue, VDesc, or VSName - - name: param - in: query - schema: - type: string - description: Alternative search parameter (alias for search) - responses: - '200': - description: List of user value set items - content: - application/json: - schema: - type: object - properties: - status: - type: string - data: - type: array - items: - $ref: '#/components/schemas/ValueSetItem' - - post: - tags: [ValueSets] - summary: Create user value set item - description: Create value set item in database (user-defined) - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - VSetID - properties: - SiteID: - type: integer - description: Site reference (default 1) - VSetID: - type: integer - description: Reference to value set definition (required) - VOrder: - type: integer - description: Display order (default 0) - VValue: - type: string - description: The value code - VDesc: - type: string - description: The display description/label - responses: - '201': - description: User value set item created - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - $ref: '#/components/schemas/ValueSetItem' - - /api/valueset/user/items/{id}: - get: - tags: [ValueSets] - summary: Get user value set item by ID - description: Get value set item from database (user-defined) - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: User value set item details - content: - application/json: - schema: - type: object - properties: - status: - type: string - data: - $ref: '#/components/schemas/ValueSetItem' - - put: - tags: [ValueSets] - summary: Update user value set item - description: Update value set item in database (user-defined) - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - requestBody: - required: true - content: - application/json: - schema: - type: object - properties: - SiteID: - type: integer - description: Site reference - VSetID: - type: integer - description: Reference to value set definition - VOrder: - type: integer - description: Display order - VValue: - type: string - description: The value code - VDesc: - type: string - description: The display description/label - responses: - '200': - description: User value set item updated - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - $ref: '#/components/schemas/ValueSetItem' - - delete: - tags: [ValueSets] - summary: Delete user value set item - description: Delete value set item from database (user-defined) - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: User value set item deleted - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - - /api/valueset/user/def: - get: - tags: [ValueSets] - summary: List user value set definitions - description: List value set definitions from database (user-defined) - security: - - bearerAuth: [] - parameters: - - name: search - in: query - schema: - type: string - description: Optional search term to filter definitions - - name: page - in: query - schema: - type: integer - default: 1 - description: Page number for pagination - - name: limit - in: query - schema: - type: integer - default: 100 - description: Number of items per page - responses: - '200': - description: List of user value set definitions - content: - application/json: - schema: - type: object - properties: - status: - type: string - data: - type: array - items: - $ref: '#/components/schemas/ValueSetDef' - meta: - type: object - properties: - total: - type: integer - page: - type: integer - limit: - type: integer - - post: - tags: [ValueSets] - summary: Create user value set definition - description: Create value set definition in database (user-defined) - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - properties: - SiteID: - type: integer - description: Site reference (default 1) - VSName: - type: string - description: Value set name - VSDesc: - type: string - description: Value set description - responses: - '201': - description: User value set definition created - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - $ref: '#/components/schemas/ValueSetDef' - - /api/valueset/user/def/{id}: - get: - tags: [ValueSets] - summary: Get user value set definition by ID - description: Get value set definition from database (user-defined) - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: User value set definition details - content: - application/json: - schema: - type: object - properties: - status: - type: string - data: - $ref: '#/components/schemas/ValueSetDef' - - put: - tags: [ValueSets] - summary: Update user value set definition - description: Update value set definition in database (user-defined) - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - requestBody: - required: true - content: - application/json: - schema: - type: object - properties: - SiteID: - type: integer - description: Site reference - VSName: - type: string - description: Value set name - VSDesc: - type: string - description: Value set description - responses: - '200': - description: User value set definition updated - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - $ref: '#/components/schemas/ValueSetDef' - - delete: - tags: [ValueSets] - summary: Delete user value set definition - description: Delete value set definition from database (user-defined) - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - responses: - '200': - description: User value set definition deleted - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - - # ======================================== - # Master Data Routes - # ======================================== - /api/location: - get: - tags: [Master Data] - summary: List locations - security: - - bearerAuth: [] - parameters: - - name: LocCode - in: query - schema: - type: string - description: Filter by location code - - name: LocName - in: query - schema: - type: string - description: Filter by location name (searches in LocFull) - responses: - '200': - description: List of locations - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - type: array - items: - $ref: '#/components/schemas/Location' - - post: - tags: [Master Data] - summary: Create location - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - LocCode - - LocFull - properties: - SiteID: - type: integer - LocCode: - type: string - maxLength: 6 - Parent: - type: integer - LocFull: - type: string - maxLength: 255 - Description: - type: string - maxLength: 255 - LocType: - type: string - responses: - '201': - description: Location created - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - type: object - - patch: - tags: [Master Data] - summary: Update location - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - LocCode - - LocFull - properties: - LocationID: - type: integer - SiteID: - type: integer - LocCode: - type: string - maxLength: 6 - Parent: - type: integer - LocFull: - type: string - maxLength: 255 - Description: - type: string - maxLength: 255 - LocType: - type: string - responses: - '200': - description: Location updated - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - type: object - - delete: - tags: [Master Data] - summary: Delete location - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - LocationID - properties: - LocationID: - type: integer - responses: - '200': - description: Location deleted - - /api/location/{id}: - get: - tags: [Master Data] - summary: Get location by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - description: LocationID (primary key) - responses: - '200': - description: Location details - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - $ref: '#/components/schemas/Location' - - /api/contact: - get: - tags: [Master Data] - summary: List contacts - security: - - bearerAuth: [] - responses: - '200': - description: List of contacts - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - type: array - items: - $ref: '#/components/schemas/Contact' - - post: - tags: [Master Data] - summary: Create contact - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - NameFirst - properties: - NameFirst: - type: string - description: First name (required) - NameLast: - type: string - description: Last name - Title: - type: string - description: Title (e.g., Dr, Mr, Mrs) - Initial: - type: string - description: Middle initial - Birthdate: - type: string - format: date-time - EmailAddress1: - type: string - format: email - EmailAddress2: - type: string - format: email - Phone: - type: string - MobilePhone1: - type: string - MobilePhone2: - type: string - Specialty: - type: string - SubSpecialty: - type: string - responses: - '201': - description: Contact created - - patch: - tags: [Master Data] - summary: Update contact - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - NameFirst - properties: - ContactID: - type: integer - NameFirst: - type: string - NameLast: - type: string - Title: - type: string - Initial: - type: string - Birthdate: - type: string - format: date-time - EmailAddress1: - type: string - format: email - EmailAddress2: - type: string - format: email - Phone: - type: string - MobilePhone1: - type: string - MobilePhone2: - type: string - Specialty: - type: string - SubSpecialty: - type: string - responses: - '200': - description: Contact updated - - delete: - tags: [Master Data] - summary: Delete contact - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - ContactID - properties: - ContactID: - type: integer - responses: - '200': - description: Contact deleted - - /api/contact/{id}: - get: - tags: [Master Data] - summary: Get contact by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - description: ContactID (primary key) - responses: - '200': - description: Contact details - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - $ref: '#/components/schemas/Contact' - - /api/occupation: - get: - tags: [Master Data] - summary: List occupations - security: - - bearerAuth: [] - responses: - '200': - description: List of occupations - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - type: array - items: - $ref: '#/components/schemas/Occupation' - - post: - tags: [Master Data] - summary: Create occupation - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - OccCode - - OccText - properties: - OccCode: - type: string - description: Occupation code (required) - OccText: - type: string - description: Occupation name/text (required) - Description: - type: string - description: Additional description - responses: - '201': - description: Occupation created - - patch: - tags: [Master Data] - summary: Update occupation - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - OccCode - - OccText - properties: - OccupationID: - type: integer - OccCode: - type: string - OccText: - type: string - Description: - type: string - responses: - '200': - description: Occupation updated - - /api/occupation/{id}: - get: - tags: [Master Data] - summary: Get occupation by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - description: OccupationID (primary key) - responses: - '200': - description: Occupation details - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - $ref: '#/components/schemas/Occupation' - - /api/medicalspecialty: - get: - tags: [Master Data] - summary: List medical specialties - security: - - bearerAuth: [] - responses: - '200': - description: List of medical specialties - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - type: array - items: - $ref: '#/components/schemas/MedicalSpecialty' - - post: - tags: [Master Data] - summary: Create medical specialty - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - SpecialtyText - properties: - SpecialtyText: - type: string - description: Specialty name/text (required) - Parent: - type: integer - description: Parent specialty ID - Title: - type: string - description: Title/abbreviation - responses: - '201': - description: Medical specialty created - - patch: - tags: [Master Data] - summary: Update medical specialty - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - SpecialtyText - properties: - SpecialtyID: - type: integer - SpecialtyText: - type: string - Parent: - type: integer - Title: - type: string - responses: - '200': - description: Medical specialty updated - - /api/medicalspecialty/{id}: - get: - tags: [Master Data] - summary: Get medical specialty by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - description: SpecialtyID (primary key) - responses: - '200': - description: Medical specialty details - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - $ref: '#/components/schemas/MedicalSpecialty' - - /api/counter: - get: - tags: [Master Data] - summary: List counters - security: - - bearerAuth: [] - responses: - '200': - description: List of counters - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - type: array - items: - $ref: '#/components/schemas/Counter' - - post: - tags: [Master Data] - summary: Create counter - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - properties: - CounterDesc: - type: string - description: Counter description/name - CounterValue: - type: integer - description: Current counter value - CounterStart: - type: integer - description: Starting value - CounterEnd: - type: integer - description: Ending value (for auto-reset) - CounterReset: - type: string - description: Reset pattern (D=Daily, M=Monthly, Y=Yearly) - responses: - '201': - description: Counter created - - patch: - tags: [Master Data] - summary: Update counter - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - properties: - CounterID: - type: integer - CounterDesc: - type: string - CounterValue: - type: integer - CounterStart: - type: integer - CounterEnd: - type: integer - CounterReset: - type: string - responses: - '200': - description: Counter updated - - delete: - tags: [Master Data] - summary: Delete counter - security: - - bearerAuth: [] - requestBody: - required: true - content: - application/json: - schema: - type: object - required: - - CounterID - properties: - CounterID: - type: integer - responses: - '200': - description: Counter deleted - - /api/counter/{id}: - get: - tags: [Master Data] - summary: Get counter by ID - security: - - bearerAuth: [] - parameters: - - name: id - in: path - required: true - schema: - type: integer - description: CounterID (primary key) - responses: - '200': - description: Counter details - content: - application/json: - schema: - type: object - properties: - status: - type: string - message: - type: string - data: - $ref: '#/components/schemas/Counter' - - /api/areageo: - get: - tags: [Master Data] - summary: List geographical areas - security: - - bearerAuth: [] - responses: - '200': - description: List of geographical areas - - /api/areageo/provinces: - get: - tags: [Master Data] - summary: Get list of provinces - security: - - bearerAuth: [] - responses: - '200': - description: List of provinces - - /api/areageo/cities: - get: - tags: [Master Data] - summary: Get list of cities - security: - - bearerAuth: [] - parameters: - - name: ProvinceID - in: query - schema: - type: integer - responses: - '200': - description: List of cities - - # ======================================== - # Dashboard & Results (Protected) - # ======================================== - /api/dashboard: - get: - tags: [Dashboard] - summary: Get dashboard summary - security: - - bearerAuth: [] - responses: - '200': - description: Dashboard summary data - content: - application/json: - schema: - $ref: '#/components/schemas/DashboardSummary' - - /api/result: - get: - tags: [Results] - summary: Get patient results - security: - - bearerAuth: [] - parameters: - - name: PatientID - in: query - schema: - type: string - - name: page - in: query - schema: - type: integer - responses: - '200': - description: List of results - - /api/sample: - get: - tags: [Specimen] - summary: Get samples - security: - - bearerAuth: [] - parameters: - - name: status - in: query - schema: - type: string - responses: - '200': - description: List of samples - - # ======================================== - # Demo Routes (No Auth) - # ======================================== - /api/demo/order: - post: - tags: [Demo] - summary: Create demo order (no authentication) - description: Test endpoint for creating orders without authentication - requestBody: - required: true - content: - application/json: - schema: - type: object - properties: - PatientID: - type: string - Tests: - type: array - items: - type: object - responses: - '201': - description: Demo order created - - /api/demo/orders: - get: - tags: [Demo] - summary: List demo orders (no authentication) - responses: - '200': - description: List of demo orders \ No newline at end of file + $ref: './components/schemas/common.yaml#/DashboardSummary' + + # Authentication schemas + LoginRequest: + $ref: './components/schemas/authentication.yaml#/LoginRequest' + LoginResponse: + $ref: './components/schemas/authentication.yaml#/LoginResponse' + RegisterRequest: + $ref: './components/schemas/authentication.yaml#/RegisterRequest' + + # Patient schemas + Patient: + $ref: './components/schemas/patient.yaml#/Patient' + PatientIdentifier: + $ref: './components/schemas/patient.yaml#/PatientIdentifier' + LinkedPatient: + $ref: './components/schemas/patient.yaml#/LinkedPatient' + Custodian: + $ref: './components/schemas/patient.yaml#/Custodian' + PatAttEntry: + $ref: './components/schemas/patient.yaml#/PatAttEntry' + PatientListResponse: + $ref: './components/schemas/patient.yaml#/PatientListResponse' + + # Patient Visit schemas + PatientVisit: + $ref: './components/schemas/patient-visit.yaml#/PatientVisit' + PatVisitADT: + $ref: './components/schemas/patient-visit.yaml#/PatVisitADT' + + # Organization schemas + Account: + $ref: './components/schemas/organization.yaml#/Account' + Site: + $ref: './components/schemas/organization.yaml#/Site' + Discipline: + $ref: './components/schemas/organization.yaml#/Discipline' + Department: + $ref: './components/schemas/organization.yaml#/Department' + Workstation: + $ref: './components/schemas/organization.yaml#/Workstation' + + # Specimen schemas + Specimen: + $ref: './components/schemas/specimen.yaml#/Specimen' + ContainerDef: + $ref: './components/schemas/specimen.yaml#/ContainerDef' + SpecimenPrep: + $ref: './components/schemas/specimen.yaml#/SpecimenPrep' + SpecimenStatus: + $ref: './components/schemas/specimen.yaml#/SpecimenStatus' + SpecimenCollection: + $ref: './components/schemas/specimen.yaml#/SpecimenCollection' + + # Tests schemas + TestDefinition: + $ref: './components/schemas/tests.yaml#/TestDefinition' + TestMap: + $ref: './components/schemas/tests.yaml#/TestMap' + + # Orders schemas + OrderTest: + $ref: './components/schemas/orders.yaml#/OrderTest' + OrderItem: + $ref: './components/schemas/orders.yaml#/OrderItem' + + # Edge API schemas + EdgeResultRequest: + $ref: './components/schemas/edge-api.yaml#/EdgeResultRequest' + EdgeResultResponse: + $ref: './components/schemas/edge-api.yaml#/EdgeResultResponse' + EdgeOrder: + $ref: './components/schemas/edge-api.yaml#/EdgeOrder' + + # ValueSets schemas + ValueSetLibItem: + $ref: './components/schemas/valuesets.yaml#/ValueSetLibItem' + ValueSetDef: + $ref: './components/schemas/valuesets.yaml#/ValueSetDef' + ValueSetItem: + $ref: './components/schemas/valuesets.yaml#/ValueSetItem' + + # Master Data schemas + Location: + $ref: './components/schemas/master-data.yaml#/Location' + Contact: + $ref: './components/schemas/master-data.yaml#/Contact' + Occupation: + $ref: './components/schemas/master-data.yaml#/Occupation' + MedicalSpecialty: + $ref: './components/schemas/master-data.yaml#/MedicalSpecialty' + Counter: + $ref: './components/schemas/master-data.yaml#/Counter' + +# Paths are in separate files in the paths/ directory +# To view the complete API with all paths, use: api-docs.bundled.yaml +# To rebuild the bundle after changes: python bundle-api-docs.py +paths: {} diff --git a/public/bundle-api-docs.js b/public/bundle-api-docs.js new file mode 100644 index 0000000..7b4542d --- /dev/null +++ b/public/bundle-api-docs.js @@ -0,0 +1,96 @@ +#!/usr/bin/env node + +/** + * OpenAPI Documentation Bundler - Node.js Version + * + * This script merges the modular OpenAPI specification files into a single + * api-docs.bundled.yaml file that can be served to Swagger UI. + * + * It merges paths from the paths/ directory and then uses Redocly CLI to resolve + * all $ref references into inline definitions. + * + * Usage: node bundle-api-docs.js + */ + +const fs = require('fs'); +const path = require('path'); +const { execSync } = require('child_process'); + +const publicDir = __dirname; +const pathsDir = path.join(publicDir, 'paths'); +const tempFile = path.join(publicDir, 'api-docs.merged.yaml'); +const outputFile = path.join(publicDir, 'api-docs.bundled.yaml'); + +// Read the base api-docs.yaml +const apiDocsPath = path.join(publicDir, 'api-docs.yaml'); +let apiDocsContent = fs.readFileSync(apiDocsPath, 'utf8'); + +// Parse YAML manually (simple approach - looking for paths: {}) +const pathsMatch = apiDocsContent.match(/^paths:\s*\{\}/m); +if (!pathsMatch) { + console.error('Could not find empty paths section in api-docs.yaml'); + process.exit(1); +} + +// Read all path files +const pathFiles = fs.readdirSync(pathsDir) + .filter(f => f.endsWith('.yaml')) + .map(f => path.join(pathsDir, f)); + +console.log(`Found ${pathFiles.length} path files to merge...`); + +// Merge all paths content +let mergedPaths = []; +for (const filepath of pathFiles) { + const filename = path.basename(filepath); + try { + let content = fs.readFileSync(filepath, 'utf8'); + // Fix relative paths: ../components/ -> ./components/ + // because paths are now at the root level after merging + content = content.replace(/\.\.\/components\//g, './components/'); + mergedPaths.push(`# From: ${filename}\n${content}`); + console.log(` [OK] Merged paths from ${filename}`); + } catch (e) { + console.log(` [WARN] Failed to read ${filename}: ${e.message}`); + } +} + +// Replace empty paths with merged paths +const pathsYaml = mergedPaths.join('\n\n'); +const mergedContent = apiDocsContent.replace( + /^paths:\s*\{\}/m, + `paths:\n${pathsYaml.split('\n').map(line => ' ' + line).join('\n')}` +); + +// Write merged file (still has $refs) +fs.writeFileSync(tempFile, mergedContent, 'utf8'); +console.log(`\n[SUCCESS] Merged paths into: ${tempFile}`); + +// Now use Redocly CLI to resolve all $ref references +console.log('\nResolving $ref references with Redocly CLI...'); +try { + execSync(`redocly bundle "${tempFile}" -o "${outputFile}"`, { + cwd: publicDir, + stdio: 'inherit' + }); + + console.log(`\n[SUCCESS] Resolved all $ref references to: ${outputFile}`); + + // Clean up temp file + fs.unlinkSync(tempFile); + console.log(`[CLEANUP] Removed temp file: ${tempFile}`); + + // Show stats + const stats = fs.statSync(outputFile); + console.log(`\n${'='.repeat(60)}`); + console.log('Bundling complete!'); + console.log(` Output: ${outputFile}`); + console.log(` Size: ${(stats.size / 1024).toFixed(1)} KB`); + console.log(`\nYou can now serve this file to Swagger UI.`); + console.log(`${'='.repeat(60)}`); + +} catch (e) { + console.error(`\n[ERROR] Failed to run Redocly CLI: ${e.message}`); + console.error('Make sure Redocly CLI is installed: npm install -g @redocly/cli'); + process.exit(1); +} diff --git a/public/bundle-api-docs.php b/public/bundle-api-docs.php new file mode 100644 index 0000000..68c72d9 --- /dev/null +++ b/public/bundle-api-docs.php @@ -0,0 +1,55 @@ +=" + HighSign: LE + HighSignLabel: "<=" + Low: 70 + High: 100 + AgeStart: 18 + AgeEnd: 99 + Flag: N + Interpretation: Normal + TEST_numeric_thold: + summary: Technical test - threshold reference (THOLD) + value: + id: 1 + TestCode: GLU + TestName: Glucose + TestType: TEST + DisciplineID: 1 + DepartmentID: 1 + Unit: mg/dL + refnum: + - RefNumID: 2 + NumRefType: THOLD + NumRefTypeLabel: Threshold + RangeType: PANIC + RangeTypeLabel: Panic Range + Sex: '1' + SexLabel: Female + LowSign: LT + LowSignLabel: "<" + High: 40 + AgeStart: 0 + AgeEnd: 120 + Flag: L + Interpretation: Critical Low + $2: + Unit: null + reftxt: + - RefTxtID: 1 + TxtRefType: TEXT + TxtRefTypeLabel: Text + Sex: '2' + SexLabel: Male + AgeStart: 18 + AgeEnd: 99 + RefTxt: 'NORM=Normal;HYPO=Hypochromic;MACRO=Macrocytic' + Flag: N + TEST_text_vset: + summary: Technical test - text reference (VSET) + value: + id: 1 + TestCode: STAGE + TestName: Disease Stage + TestType: TEST + DisciplineID: 1 + DepartmentID: 1 + Unit: null + reftxt: + - RefTxtID: 2 + TxtRefType: VSET + TxtRefTypeLabel: Value Set + Sex: '1' + SexLabel: Female + AgeStart: 0 + AgeEnd: 120 + RefTxt: 'STG1=Stage 1;STG2=Stage 2;STG3=Stage 3;STG4=Stage 4' + Flag: N + PARAM: + summary: Parameter - no reference range allowed + value: + id: 2 + TestCode: GLU_FAST + TestName: Fasting Glucose + TestType: PARAM + DisciplineID: 1 + DepartmentID: 1 + Unit: mg/dL + $3: + Unit: null + Formula: "BUN / Creatinine" + refnum: + - RefNumID: 5 + NumRefType: NMRC + NumRefTypeLabel: Numeric + RangeType: REF + RangeTypeLabel: Reference Range + Sex: '1' + SexLabel: Female + LowSign: GE + LowSignLabel: ">=" + HighSign: LE + HighSignLabel: "<=" + Low: 10 + High: 20 + AgeStart: 18 + AgeEnd: 120 + Flag: N + Interpretation: Normal + $4: + Unit: null + Formula: "BUN / Creatinine" + refnum: + - RefNumID: 6 + NumRefType: THOLD + NumRefTypeLabel: Threshold + RangeType: PANIC + RangeTypeLabel: Panic Range + Sex: '1' + SexLabel: Female + LowSign: GT + LowSignLabel: ">" + Low: 20 + AgeStart: 18 + AgeEnd: 120 + Flag: H + Interpretation: Elevated - possible prerenal cause + + GROUP: + summary: Panel/Profile - no reference range allowed + value: + id: 4 + TestCode: LIPID + TestName: Lipid Panel + TestType: GROUP + DisciplineID: 1 + DepartmentID: 1 + Unit: null + TITLE: + summary: Section header - no reference range allowed + value: + id: 5 + TestCode: CHEM_HEADER + TestName: '--- CHEMISTRY ---' + TestType: TITLE + DisciplineID: 1 + DepartmentID: 1 + Unit: null + +TestMap: + type: object + properties: + id: + type: integer + TestMapID: + type: integer + TestCode: + type: string + HostCode: + type: string + HostName: + type: string + ClientCode: + type: string + ClientName: + type: string + HostType: + type: string + description: Host type code + HostTypeLabel: + type: string + description: Host type display text + ClientType: + type: string + description: Client type code + ClientTypeLabel: + type: string + description: Client type display text diff --git a/public/components/schemas/valuesets.yaml b/public/components/schemas/valuesets.yaml new file mode 100644 index 0000000..ef7a431 --- /dev/null +++ b/public/components/schemas/valuesets.yaml @@ -0,0 +1,77 @@ +ValueSetLibItem: + type: object + description: Library/system value set item from JSON files + properties: + value: + type: string + description: The value/key code + label: + type: string + description: The display label + +ValueSetDef: + type: object + description: User-defined value set definition (from database) + properties: + VSetID: + type: integer + description: Primary key + SiteID: + type: integer + description: Site reference + VSName: + type: string + description: Value set name + VSDesc: + type: string + description: Value set description + CreateDate: + type: string + format: date-time + description: Creation timestamp + EndDate: + type: string + format: date-time + nullable: true + description: Soft delete timestamp + ItemCount: + type: integer + description: Number of items in this value set + +ValueSetItem: + type: object + description: User-defined value set item (from database) + properties: + VID: + type: integer + description: Primary key + SiteID: + type: integer + description: Site reference + VSetID: + type: integer + description: Reference to value set definition + VOrder: + type: integer + description: Display order + VValue: + type: string + description: The value code + VDesc: + type: string + description: The display description/label + VCategory: + type: string + description: Category code + CreateDate: + type: string + format: date-time + description: Creation timestamp + EndDate: + type: string + format: date-time + nullable: true + description: Soft delete timestamp + VSName: + type: string + description: Value set name (from joined definition) diff --git a/public/paths/authentication.yaml b/public/paths/authentication.yaml new file mode 100644 index 0000000..0343fd6 --- /dev/null +++ b/public/paths/authentication.yaml @@ -0,0 +1,167 @@ +/api/auth/login: + post: + tags: [Authentication] + summary: User login + description: Authenticate user and receive JWT token via HTTP-only cookie + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/authentication.yaml#/LoginRequest' + application/x-www-form-urlencoded: + schema: + $ref: '../components/schemas/authentication.yaml#/LoginRequest' + responses: + '200': + description: Login successful + headers: + Set-Cookie: + description: JWT token in HTTP-only cookie + schema: + type: string + content: + application/json: + schema: + $ref: '../components/schemas/authentication.yaml#/LoginResponse' + '400': + description: Missing username + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/ErrorResponse' + '401': + description: Invalid credentials + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/ErrorResponse' + +/api/auth/logout: + post: + tags: [Authentication] + summary: User logout + description: Clear JWT token cookie + security: + - bearerAuth: [] + responses: + '200': + description: Logout successful + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/SuccessResponse' + +/api/auth/check: + get: + tags: [Authentication] + summary: Check authentication status + security: + - bearerAuth: [] + - cookieAuth: [] + responses: + '200': + description: Authenticated + content: + application/json: + schema: + type: object + properties: + authenticated: + type: boolean + user: + type: object + '401': + description: Not authenticated + +/api/auth/register: + post: + tags: [Authentication] + summary: Register new user + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/authentication.yaml#/RegisterRequest' + responses: + '201': + description: User created + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/SuccessResponse' + +/api/auth/change_pass: + post: + tags: [Authentication] + summary: Change password + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - current_password + - new_password + properties: + current_password: + type: string + format: password + new_password: + type: string + format: password + responses: + '200': + description: Password changed successfully + +/v2/auth/login: + post: + tags: [Authentication] + summary: V2 User login + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/authentication.yaml#/LoginRequest' + responses: + '200': + description: Login successful + content: + application/json: + schema: + $ref: '../components/schemas/authentication.yaml#/LoginResponse' + +/v2/auth/logout: + post: + tags: [Authentication] + summary: V2 User logout + responses: + '200': + description: Logout successful + +/v2/auth/check: + get: + tags: [Authentication] + summary: V2 Check authentication + responses: + '200': + description: Auth check result + +/v2/auth/register: + post: + tags: [Authentication] + summary: V2 Register new user + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/authentication.yaml#/RegisterRequest' + responses: + '201': + description: User created diff --git a/public/paths/demo.yaml b/public/paths/demo.yaml new file mode 100644 index 0000000..285b689 --- /dev/null +++ b/public/paths/demo.yaml @@ -0,0 +1,42 @@ +/api/demo/hello: + get: + tags: [Demo] + summary: Hello world endpoint + description: Simple test endpoint that returns a greeting message + responses: + '200': + description: Successful response + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: Hello, World! + +/api/demo/ping: + get: + tags: [Demo] + summary: Ping endpoint + description: Health check endpoint to verify API is running + responses: + '200': + description: API is running + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: pong + timestamp: + type: string + format: date-time diff --git a/public/paths/edge-api.yaml b/public/paths/edge-api.yaml new file mode 100644 index 0000000..30f71dc --- /dev/null +++ b/public/paths/edge-api.yaml @@ -0,0 +1,103 @@ +/api/edge/results: + post: + tags: [Edge API] + summary: Receive results from instrument (tiny-edge) + description: | + Receives instrument results and stores them in the edgeres table for processing. + This endpoint is typically called by the tiny-edge middleware connected to laboratory analyzers. + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/edge-api.yaml#/EdgeResultRequest' + responses: + '201': + description: Result received and queued + content: + application/json: + schema: + $ref: '../components/schemas/edge-api.yaml#/EdgeResultResponse' + '400': + description: Invalid JSON payload + +/api/edge/orders: + get: + tags: [Edge API] + summary: Fetch pending orders for instruments + description: Returns orders that need to be sent to laboratory instruments for testing + parameters: + - name: instrument_id + in: query + schema: + type: string + description: Filter by instrument + - name: status + in: query + schema: + type: string + enum: [pending, acknowledged] + description: Filter by status + responses: + '200': + description: List of orders + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '../components/schemas/edge-api.yaml#/EdgeOrder' + +/api/edge/orders/{orderId}/ack: + post: + tags: [Edge API] + summary: Acknowledge order delivery + description: Mark order as acknowledged by the instrument + parameters: + - name: orderId + in: path + required: true + schema: + type: integer + description: Edge order ID + responses: + '200': + description: Order acknowledged + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/SuccessResponse' + +/api/edge/status: + post: + tags: [Edge API] + summary: Log instrument status update + description: Receive status updates from laboratory instruments + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - instrument_id + - status + properties: + instrument_id: + type: string + status: + type: string + enum: [online, offline, error, maintenance] + message: + type: string + timestamp: + type: string + format: date-time + responses: + '200': + description: Status logged diff --git a/public/paths/master-data.yaml b/public/paths/master-data.yaml new file mode 100644 index 0000000..430902e --- /dev/null +++ b/public/paths/master-data.yaml @@ -0,0 +1,59 @@ +/api/location: + get: + tags: [Master Data] + summary: List locations + security: + - bearerAuth: [] + parameters: + - name: LocCode + in: query + schema: + type: string + description: Filter by location code + - name: LocName + in: query + schema: + type: string + description: Filter by location name (searches in LocFull) + responses: + '200': + description: List of locations + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + type: array + items: + $ref: '../components/schemas/master-data.yaml#/Location' + + post: + tags: [Master Data] + summary: Create location + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - LocCode + - LocFull + properties: + SiteID: + type: integer + LocCode: + type: string + maxLength: 6 + Parent: + type: integer + LocFull: + type: string + maxLength: 255 diff --git a/public/paths/orders.yaml b/public/paths/orders.yaml new file mode 100644 index 0000000..73f8017 --- /dev/null +++ b/public/paths/orders.yaml @@ -0,0 +1,150 @@ +/api/ordertest: + get: + tags: [Orders] + summary: List orders + security: + - bearerAuth: [] + parameters: + - name: page + in: query + schema: + type: integer + - name: perPage + in: query + schema: + type: integer + - name: InternalPID + in: query + schema: + type: integer + description: Filter by internal patient ID + - name: OrderStatus + in: query + schema: + type: string + enum: [ORD, SCH, ANA, VER, REV, REP] + description: | + ORD: Ordered + SCH: Scheduled + ANA: Analysis + VER: Verified + REV: Reviewed + REP: Reported + responses: + '200': + description: List of orders + + post: + tags: [Orders] + summary: Create order + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - PatientID + - Tests + properties: + PatientID: + type: string + VisitID: + type: string + Priority: + type: string + enum: [R, S, U] + description: | + R: Routine + S: Stat + U: Urgent + SiteID: + type: integer + RequestingPhysician: + type: string + Tests: + type: array + items: + type: object + properties: + TestID: + type: integer + SpecimenType: + type: string + responses: + '201': + description: Order created successfully + + patch: + tags: [Orders] + summary: Update order + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/orders.yaml#/OrderTest' + responses: + '200': + description: Order updated + + delete: + tags: [Orders] + summary: Delete order + security: + - bearerAuth: [] + responses: + '200': + description: Order deleted + +/api/ordertest/status: + post: + tags: [Orders] + summary: Update order status + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - OrderID + - OrderStatus + properties: + OrderID: + type: string + OrderStatus: + type: string + enum: [ORD, SCH, ANA, VER, REV, REP] + description: | + ORD: Ordered + SCH: Scheduled + ANA: Analysis + VER: Verified + REV: Reviewed + REP: Reported + responses: + '200': + description: Order status updated + +/api/ordertest/{id}: + get: + tags: [Orders] + summary: Get order by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: string + responses: + '200': + description: Order details diff --git a/public/paths/organization.yaml b/public/paths/organization.yaml new file mode 100644 index 0000000..f75bb15 --- /dev/null +++ b/public/paths/organization.yaml @@ -0,0 +1,367 @@ +/api/organization/account/{id}: + get: + tags: [Organization] + summary: Get account by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Account details + content: + application/json: + schema: + $ref: '../components/schemas/organization.yaml#/Account' + +/api/organization/site: + get: + tags: [Organization] + summary: List sites + security: + - bearerAuth: [] + responses: + '200': + description: List of sites + + post: + tags: [Organization] + summary: Create site + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/organization.yaml#/Site' + responses: + '201': + description: Site created + + patch: + tags: [Organization] + summary: Update site + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + SiteName: + type: string + SiteCode: + type: string + AccountID: + type: integer + responses: + '200': + description: Site updated + + delete: + tags: [Organization] + summary: Delete site + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + responses: + '200': + description: Site deleted + +/api/organization/site/{id}: + get: + tags: [Organization] + summary: Get site by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Site details + +/api/organization/discipline: + get: + tags: [Organization] + summary: List disciplines + security: + - bearerAuth: [] + responses: + '200': + description: List of disciplines + + post: + tags: [Organization] + summary: Create discipline + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/organization.yaml#/Discipline' + responses: + '201': + description: Discipline created + + patch: + tags: [Organization] + summary: Update discipline + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + DisciplineName: + type: string + DisciplineCode: + type: string + responses: + '200': + description: Discipline updated + + delete: + tags: [Organization] + summary: Delete discipline + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + responses: + '200': + description: Discipline deleted + +/api/organization/discipline/{id}: + get: + tags: [Organization] + summary: Get discipline by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Discipline details + +/api/organization/department: + get: + tags: [Organization] + summary: List departments + security: + - bearerAuth: [] + responses: + '200': + description: List of departments + + post: + tags: [Organization] + summary: Create department + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/organization.yaml#/Department' + responses: + '201': + description: Department created + + patch: + tags: [Organization] + summary: Update department + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + DeptName: + type: string + DeptCode: + type: string + SiteID: + type: integer + responses: + '200': + description: Department updated + + delete: + tags: [Organization] + summary: Delete department + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + responses: + '200': + description: Department deleted + +/api/organization/department/{id}: + get: + tags: [Organization] + summary: Get department by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Department details + +/api/organization/workstation: + get: + tags: [Organization] + summary: List workstations + security: + - bearerAuth: [] + responses: + '200': + description: List of workstations + + post: + tags: [Organization] + summary: Create workstation + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/organization.yaml#/Workstation' + responses: + '201': + description: Workstation created + + patch: + tags: [Organization] + summary: Update workstation + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + WorkstationName: + type: string + WorkstationCode: + type: string + SiteID: + type: integer + DepartmentID: + type: integer + responses: + '200': + description: Workstation updated + + delete: + tags: [Organization] + summary: Delete workstation + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - id + properties: + id: + type: integer + responses: + '200': + description: Workstation deleted + +/api/organization/workstation/{id}: + get: + tags: [Organization] + summary: Get workstation by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Workstation details diff --git a/public/paths/patient-visits.yaml b/public/paths/patient-visits.yaml new file mode 100644 index 0000000..4ac08cb --- /dev/null +++ b/public/paths/patient-visits.yaml @@ -0,0 +1,487 @@ +/api/patvisit: + get: + tags: [Patient Visits] + summary: List patient visits + security: + - bearerAuth: [] + parameters: + - name: page + in: query + schema: + type: integer + - name: perPage + in: query + schema: + type: integer + responses: + '200': + description: List of patient visits + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + type: array + items: + $ref: '../components/schemas/patient-visit.yaml#/PatientVisit' + total: + type: integer + description: Total number of records + page: + type: integer + description: Current page number + per_page: + type: integer + description: Number of records per page + + post: + tags: [Patient Visits] + summary: Create patient visit + description: | + Creates a new patient visit. PVID is auto-generated with 'DV' prefix if not provided. + Can optionally include PatDiag (diagnosis) and PatVisitADT (ADT information). + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - InternalPID + properties: + PVID: + type: string + description: Visit ID (auto-generated with DV prefix if not provided) + InternalPID: + type: integer + description: Patient ID (required) + EpisodeID: + type: string + description: Episode identifier + SiteID: + type: integer + description: Site reference + PatDiag: + type: object + description: Optional diagnosis information + properties: + DiagCode: + type: string + Diagnosis: + type: string + PatVisitADT: + type: object + description: Optional ADT information + properties: + ADTCode: + type: string + enum: [A01, A02, A03, A04, A08] + LocationID: + type: integer + AttDoc: + type: integer + RefDoc: + type: integer + AdmDoc: + type: integer + CnsDoc: + type: integer + responses: + '201': + description: Visit created successfully + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + type: object + properties: + PVID: + type: string + InternalPVID: + type: integer + + patch: + tags: [Patient Visits] + summary: Update patient visit + description: | + Updates an existing patient visit. InternalPVID is required. + Can update main visit data, PatDiag, and add new PatVisitADT records. + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - InternalPVID + properties: + InternalPVID: + type: integer + description: Visit ID (required) + PVID: + type: string + InternalPID: + type: integer + EpisodeID: + type: string + SiteID: + type: integer + PatDiag: + type: object + description: Diagnosis information (will update if exists) + properties: + DiagCode: + type: string + Diagnosis: + type: string + PatVisitADT: + type: array + description: Array of ADT records to add (new records only) + items: + type: object + properties: + ADTCode: + type: string + enum: [A01, A02, A03, A04, A08] + LocationID: + type: integer + AttDoc: + type: integer + RefDoc: + type: integer + AdmDoc: + type: integer + CnsDoc: + type: integer + sequence: + type: integer + description: Used for ordering multiple ADT records + responses: + '200': + description: Visit updated successfully + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + type: object + properties: + PVID: + type: string + InternalPVID: + type: integer + + delete: + tags: [Patient Visits] + summary: Delete patient visit + security: + - bearerAuth: [] + responses: + '200': + description: Visit deleted successfully + +/api/patvisit/{id}: + get: + tags: [Patient Visits] + summary: Get visit by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: string + description: PVID (visit identifier like DV00001) + responses: + '200': + description: Visit details + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + $ref: '../components/schemas/patient-visit.yaml#/PatientVisit' + +/api/patvisit/patient/{patientId}: + get: + tags: [Patient Visits] + summary: Get visits by patient ID + security: + - bearerAuth: [] + parameters: + - name: patientId + in: path + required: true + schema: + type: integer + description: Internal Patient ID (InternalPID) + responses: + '200': + description: Patient visits list + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '../components/schemas/patient-visit.yaml#/PatientVisit' + +/api/patvisitadt: + post: + tags: [Patient Visits] + summary: Create ADT record + description: Create a new Admission/Discharge/Transfer record + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/patient-visit.yaml#/PatVisitADT' + responses: + '201': + description: ADT record created successfully + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/SuccessResponse' + + patch: + tags: [Patient Visits] + summary: Update ADT record + description: Update an existing ADT record + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/patient-visit.yaml#/PatVisitADT' + responses: + '200': + description: ADT record updated successfully + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/SuccessResponse' + + delete: + tags: [Patient Visits] + summary: Delete ADT visit (soft delete) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - PVADTID + properties: + PVADTID: + type: integer + description: ADT record ID to delete + responses: + '200': + description: ADT visit deleted successfully + +/api/patvisitadt/visit/{visitId}: + get: + tags: [Patient Visits] + summary: Get ADT history by visit ID + description: Retrieve the complete Admission/Discharge/Transfer history for a visit, including all locations and doctors + security: + - bearerAuth: [] + parameters: + - name: visitId + in: path + required: true + schema: + type: integer + description: Internal Visit ID (InternalPVID) + responses: + '200': + description: ADT history retrieved successfully + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: ADT history retrieved + data: + type: array + items: + type: object + properties: + PVADTID: + type: integer + InternalPVID: + type: integer + ADTCode: + type: string + enum: [A01, A02, A03, A04, A08] + LocationID: + type: integer + LocationName: + type: string + AttDoc: + type: integer + AttDocFirstName: + type: string + AttDocLastName: + type: string + RefDoc: + type: integer + RefDocFirstName: + type: string + RefDocLastName: + type: string + AdmDoc: + type: integer + AdmDocFirstName: + type: string + AdmDocLastName: + type: string + CnsDoc: + type: integer + CnsDocFirstName: + type: string + CnsDocLastName: + type: string + CreateDate: + type: string + format: date-time + EndDate: + type: string + format: date-time + delete: + tags: [Patient Visits] + summary: Delete ADT visit (soft delete) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - PVADTID + properties: + PVADTID: + type: integer + description: ADT record ID to delete + responses: + '200': + description: ADT visit deleted successfully + +/api/patvisitadt/{id}: + get: + tags: [Patient Visits] + summary: Get ADT record by ID + description: Retrieve a single ADT record by its ID, including location and doctor details + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: ADT record ID (PVADTID) + responses: + '200': + description: ADT record retrieved successfully + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: ADT record retrieved + data: + type: object + properties: + PVADTID: + type: integer + InternalPVID: + type: integer + ADTCode: + type: string + enum: [A01, A02, A03, A04, A08] + LocationID: + type: integer + LocationName: + type: string + AttDoc: + type: integer + AttDocFirstName: + type: string + AttDocLastName: + type: string + RefDoc: + type: integer + RefDocFirstName: + type: string + RefDocLastName: + type: string + AdmDoc: + type: integer + AdmDocFirstName: + type: string + AdmDocLastName: + type: string + CnsDoc: + type: integer + CnsDocFirstName: + type: string + CnsDocLastName: + type: string + CreateDate: + type: string + format: date-time + EndDate: + type: string + format: date-time diff --git a/public/paths/patients.yaml b/public/paths/patients.yaml new file mode 100644 index 0000000..30e1da8 --- /dev/null +++ b/public/paths/patients.yaml @@ -0,0 +1,163 @@ +/api/patient: + get: + tags: [Patients] + summary: List patients + security: + - bearerAuth: [] + parameters: + - name: page + in: query + schema: + type: integer + default: 1 + - name: perPage + in: query + schema: + type: integer + default: 20 + - name: InternalPID + in: query + schema: + type: integer + description: Filter by internal patient ID + - name: PatientID + in: query + schema: + type: string + description: Filter by patient ID + - name: Name + in: query + schema: + type: string + description: Search by patient name + - name: Birthdate + in: query + schema: + type: string + format: date + description: Filter by birthdate (YYYY-MM-DD) + responses: + '200': + description: List of patients + content: + application/json: + schema: + $ref: '../components/schemas/patient.yaml#/PatientListResponse' + + post: + tags: [Patients] + summary: Create new patient + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/patient.yaml#/Patient' + responses: + '201': + description: Patient created successfully + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/SuccessResponse' + '422': + description: Validation error + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/ErrorResponse' + + patch: + tags: [Patients] + summary: Update patient + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/patient.yaml#/Patient' + responses: + '200': + description: Patient updated successfully + + delete: + tags: [Patients] + summary: Delete patient (soft delete) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - InternalPID + properties: + InternalPID: + type: integer + description: Internal patient record ID + responses: + '200': + description: Patient deleted successfully + +/api/patient/check: + get: + tags: [Patients] + summary: Check if patient exists + security: + - bearerAuth: [] + parameters: + - name: PatientID + in: query + schema: + type: string + description: Patient ID to check + - name: EmailAddress1 + in: query + schema: + type: string + format: email + description: Email address to check + responses: + '200': + description: Patient check result + content: + application/json: + schema: + type: object + properties: + exists: + type: boolean + data: + $ref: '../components/schemas/patient.yaml#/Patient' + +/api/patient/{id}: + get: + tags: [Patients] + summary: Get patient by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: Internal patient record ID + responses: + '200': + description: Patient details + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + $ref: '../components/schemas/patient.yaml#/Patient' diff --git a/public/paths/results.yaml b/public/paths/results.yaml new file mode 100644 index 0000000..c7407f8 --- /dev/null +++ b/public/paths/results.yaml @@ -0,0 +1,263 @@ +/api/results: + get: + tags: [Results] + summary: Get patient results + description: Retrieve patient test results with optional filters + security: + - bearerAuth: [] + parameters: + - name: InternalPID + in: query + schema: + type: integer + description: Filter by internal patient ID + - name: OrderID + in: query + schema: + type: string + description: Filter by order ID + - name: TestCode + in: query + schema: + type: string + description: Filter by test code + - name: date_from + in: query + schema: + type: string + format: date + description: Filter results from date (YYYY-MM-DD) + - name: date_to + in: query + schema: + type: string + format: date + description: Filter results to date (YYYY-MM-DD) + - name: verified_only + in: query + schema: + type: boolean + default: false + description: Return only verified results + responses: + '200': + description: List of patient results + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + type: object + properties: + ResultID: + type: integer + InternalPID: + type: integer + OrderID: + type: string + TestID: + type: integer + TestCode: + type: string + TestName: + type: string + ResultValue: + type: string + Unit: + type: string + ReferenceRange: + type: string + AbnormalFlag: + type: string + Verified: + type: boolean + VerifiedBy: + type: string + VerifiedDate: + type: string + format: date-time + ResultDate: + type: string + format: date-time + + post: + tags: [Results] + summary: Create or update result + description: Create a new result or update an existing result entry + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - InternalPID + - TestID + - ResultValue + properties: + InternalPID: + type: integer + OrderID: + type: string + TestID: + type: integer + ResultValue: + type: string + Unit: + type: string + AbnormalFlag: + type: string + enum: [H, L, N, A, C] + description: H=High, L=Low, N=Normal, A=Abnormal, C=Critical + responses: + '201': + description: Result created successfully + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/SuccessResponse' + +/api/results/{id}: + get: + tags: [Results] + summary: Get result by ID + description: Retrieve a specific result entry by its ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: Result ID + responses: + '200': + description: Result details + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: object + properties: + ResultID: + type: integer + InternalPID: + type: integer + OrderID: + type: string + TestID: + type: integer + TestCode: + type: string + TestName: + type: string + ResultValue: + type: string + Unit: + type: string + ReferenceRange: + type: string + AbnormalFlag: + type: string + Verified: + type: boolean + VerifiedBy: + type: string + VerifiedDate: + type: string + format: date-time + ResultDate: + type: string + format: date-time + + patch: + tags: [Results] + summary: Update result + description: Update an existing result entry + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: Result ID + requestBody: + required: true + content: + application/json: + schema: + type: object + properties: + ResultValue: + type: string + Unit: + type: string + AbnormalFlag: + type: string + enum: [H, L, N, A, C] + Verified: + type: boolean + responses: + '200': + description: Result updated successfully + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/SuccessResponse' + + delete: + tags: [Results] + summary: Delete result + description: Soft delete a result entry + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: Result ID + responses: + '200': + description: Result deleted successfully + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/SuccessResponse' + +/api/results/{id}/verify: + post: + tags: [Results] + summary: Verify result + description: Mark a result as verified by the current user + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + description: Result ID + responses: + '200': + description: Result verified successfully + content: + application/json: + schema: + $ref: '../components/schemas/common.yaml#/SuccessResponse' diff --git a/public/paths/specimen.yaml b/public/paths/specimen.yaml new file mode 100644 index 0000000..29d560e --- /dev/null +++ b/public/paths/specimen.yaml @@ -0,0 +1,289 @@ +/api/specimen: + get: + tags: [Specimen] + summary: List specimens + security: + - bearerAuth: [] + responses: + '200': + description: List of specimens + + post: + tags: [Specimen] + summary: Create specimen + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/specimen.yaml#/Specimen' + responses: + '201': + description: Specimen created + + patch: + tags: [Specimen] + summary: Update specimen + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/specimen.yaml#/Specimen' + responses: + '200': + description: Specimen updated + +/api/specimen/{id}: + get: + tags: [Specimen] + summary: Get specimen by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Specimen details + +/api/specimen/container: + get: + tags: [Specimen] + summary: List container definitions + security: + - bearerAuth: [] + responses: + '200': + description: List of container definitions + + post: + tags: [Specimen] + summary: Create container definition + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/specimen.yaml#/ContainerDef' + responses: + '201': + description: Container definition created + + patch: + tags: [Specimen] + summary: Update container definition + security: + - bearerAuth: [] + responses: + '200': + description: Container definition updated + +/api/specimen/container/{id}: + get: + tags: [Specimen] + summary: Get container definition by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Container definition details + +/api/specimen/containerdef: + get: + tags: [Specimen] + summary: List container definitions (alias) + security: + - bearerAuth: [] + responses: + '200': + description: List of container definitions + + post: + tags: [Specimen] + summary: Create container definition (alias) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/specimen.yaml#/ContainerDef' + responses: + '201': + description: Container definition created + + patch: + tags: [Specimen] + summary: Update container definition (alias) + security: + - bearerAuth: [] + responses: + '200': + description: Container definition updated + +/api/specimen/prep: + get: + tags: [Specimen] + summary: List specimen preparations + security: + - bearerAuth: [] + responses: + '200': + description: List of specimen preparations + + post: + tags: [Specimen] + summary: Create specimen preparation + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/specimen.yaml#/SpecimenPrep' + responses: + '201': + description: Specimen preparation created + + patch: + tags: [Specimen] + summary: Update specimen preparation + security: + - bearerAuth: [] + responses: + '200': + description: Specimen preparation updated + +/api/specimen/prep/{id}: + get: + tags: [Specimen] + summary: Get specimen preparation by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Specimen preparation details + +/api/specimen/status: + get: + tags: [Specimen] + summary: List specimen statuses + security: + - bearerAuth: [] + responses: + '200': + description: List of specimen statuses + + post: + tags: [Specimen] + summary: Create specimen status + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/specimen.yaml#/SpecimenStatus' + responses: + '201': + description: Specimen status created + + patch: + tags: [Specimen] + summary: Update specimen status + security: + - bearerAuth: [] + responses: + '200': + description: Specimen status updated + +/api/specimen/status/{id}: + get: + tags: [Specimen] + summary: Get specimen status by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Specimen status details + +/api/specimen/collection: + get: + tags: [Specimen] + summary: List specimen collection methods + security: + - bearerAuth: [] + responses: + '200': + description: List of collection methods + + post: + tags: [Specimen] + summary: Create specimen collection method + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/specimen.yaml#/SpecimenCollection' + responses: + '201': + description: Collection method created + + patch: + tags: [Specimen] + summary: Update specimen collection method + security: + - bearerAuth: [] + responses: + '200': + description: Collection method updated + +/api/specimen/collection/{id}: + get: + tags: [Specimen] + summary: Get specimen collection method by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Collection method details diff --git a/public/paths/tests.yaml b/public/paths/tests.yaml new file mode 100644 index 0000000..8a6bfb1 --- /dev/null +++ b/public/paths/tests.yaml @@ -0,0 +1,113 @@ +/api/tests: + get: + tags: [Tests] + summary: List test definitions + security: + - bearerAuth: [] + parameters: + - name: page + in: query + schema: + type: integer + default: 1 + description: Page number for pagination + - name: perPage + in: query + schema: + type: integer + default: 20 + description: Number of items per page + - name: SiteID + in: query + schema: + type: integer + description: Filter by site ID + - name: TestType + in: query + schema: + type: string + enum: [TEST, PARAM, CALC, GROUP, TITLE] + description: Filter by test type + - name: VisibleScr + in: query + schema: + type: integer + enum: [0, 1] + description: Filter by screen visibility (0=hidden, 1=visible) + - name: VisibleRpt + in: query + schema: + type: integer + enum: [0, 1] + description: Filter by report visibility (0=hidden, 1=visible) + - name: search + in: query + schema: + type: string + description: Search by test code or name + responses: + '200': + description: List of test definitions + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '../components/schemas/tests.yaml#/TestDefinition' + pagination: + type: object + properties: + total: + type: integer + description: Total number of records matching the query + + post: + tags: [Tests] + summary: Create test definition + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/tests.yaml#/TestDefinition' + responses: + '201': + description: Test definition created + + patch: + tags: [Tests] + summary: Update test definition + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + $ref: '../components/schemas/tests.yaml#/TestDefinition' + responses: + '200': + description: Test definition updated + +/api/tests/{id}: + get: + tags: [Tests] + summary: Get test definition by ID + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: Test definition details diff --git a/public/paths/valuesets.yaml b/public/paths/valuesets.yaml new file mode 100644 index 0000000..82bea87 --- /dev/null +++ b/public/paths/valuesets.yaml @@ -0,0 +1,498 @@ +/api/valueset: + get: + tags: [ValueSets] + summary: List lib value sets + description: List all library/system value sets from JSON files with item counts. Returns an object where keys are value set names and values are item counts. + security: + - bearerAuth: [] + parameters: + - name: search + in: query + schema: + type: string + description: Optional search term to filter value set names + responses: + '200': + description: List of lib value sets with item counts + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + data: + type: object + additionalProperties: + type: integer + description: Number of items in each value set + example: + sex: 3 + marital_status: 6 + order_status: 6 + +/api/valueset/{key}: + get: + tags: [ValueSets] + summary: Get lib value set by key + description: | + Get a specific library/system value set from JSON files. + + **Available value set keys:** + - `activity_result` - Activity Result + - `additive` - Additive + - `adt_event` - ADT Event + - `area_class` - Area Class + - `body_site` - Body Site + - `collection_method` - Collection Method + - `container_cap_color` - Container Cap Color + - `container_class` - Container Class + - `container_size` - Container Size + - `country` - Country + - `death_indicator` - Death Indicator + - `did_type` - DID Type + - `enable_disable` - Enable/Disable + - `entity_type` - Entity Type + - `ethnic` - Ethnic + - `fasting_status` - Fasting Status + - `formula_language` - Formula Language + - `generate_by` - Generate By + - `identifier_type` - Identifier Type + - `location_type` - Location Type + - `marital_status` - Marital Status + - `math_sign` - Math Sign + - `numeric_ref_type` - Numeric Reference Type + - `operation` - Operation (CRUD) + - `order_priority` - Order Priority + - `order_status` - Order Status + - `race` - Race (Ethnicity) + - `range_type` - Range Type + - `reference_type` - Reference Type + - `religion` - Religion + - `requested_entity` - Requested Entity + - `result_type` - Result Type + - `result_unit` - Result Unit + - `sex` - Sex + - `site_class` - Site Class + - `site_type` - Site Type + - `specimen_activity` - Specimen Activity + - `specimen_condition` - Specimen Condition + - `specimen_role` - Specimen Role + - `specimen_status` - Specimen Status + - `specimen_type` - Specimen Type + - `test_activity` - Test Activity + - `test_type` - Test Type + - `text_ref_type` - Text Reference Type + - `unit` - Unit + - `v_category` - VCategory + - `ws_type` - Workstation Type + security: + - bearerAuth: [] + parameters: + - name: key + in: path + required: true + schema: + type: string + enum: [activity_result, additive, adt_event, area_class, body_site, collection_method, container_cap_color, container_class, container_size, country, death_indicator, did_type, enable_disable, entity_type, ethnic, fasting_status, formula_language, generate_by, identifier_type, location_type, marital_status, math_sign, numeric_ref_type, operation, order_priority, order_status, race, range_type, reference_type, religion, requested_entity, result_type, result_unit, sex, site_class, site_type, specimen_activity, specimen_condition, specimen_role, specimen_status, specimen_type, test_activity, test_type, text_ref_type, unit, v_category, ws_type] + description: Value set key name + responses: + '200': + description: Lib value set details + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '../components/schemas/valuesets.yaml#/ValueSetLibItem' + +/api/valueset/refresh: + post: + tags: [ValueSets] + summary: Refresh lib ValueSet cache + description: Clear and reload the library/system ValueSet cache from JSON files. Call this after modifying JSON files in app/Libraries/Data/. + security: + - bearerAuth: [] + responses: + '200': + description: Lib ValueSet cache refreshed + content: + application/json: + schema: + type: object + properties: + status: + type: string + example: success + message: + type: string + example: Cache cleared + +/api/valueset/user/items: + get: + tags: [ValueSets] + summary: List user value set items + description: List value set items from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: VSetID + in: query + schema: + type: integer + description: Filter by ValueSet ID + - name: search + in: query + schema: + type: string + description: Search term to filter by VValue, VDesc, or VSName + - name: param + in: query + schema: + type: string + description: Alternative search parameter (alias for search) + responses: + '200': + description: List of user value set items + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '../components/schemas/valuesets.yaml#/ValueSetItem' + + post: + tags: [ValueSets] + summary: Create user value set item + description: Create value set item in database (user-defined) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + required: + - VSetID + properties: + SiteID: + type: integer + description: Site reference (default 1) + VSetID: + type: integer + description: Reference to value set definition (required) + VOrder: + type: integer + description: Display order (default 0) + VValue: + type: string + description: The value code + VDesc: + type: string + description: The display description/label + responses: + '201': + description: User value set item created + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + $ref: '../components/schemas/valuesets.yaml#/ValueSetItem' + +/api/valueset/user/items/{id}: + get: + tags: [ValueSets] + summary: Get user value set item by ID + description: Get value set item from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: User value set item details + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + $ref: '../components/schemas/valuesets.yaml#/ValueSetItem' + + put: + tags: [ValueSets] + summary: Update user value set item + description: Update value set item in database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + requestBody: + required: true + content: + application/json: + schema: + type: object + properties: + SiteID: + type: integer + description: Site reference + VSetID: + type: integer + description: Reference to value set definition + VOrder: + type: integer + description: Display order + VValue: + type: string + description: The value code + VDesc: + type: string + description: The display description/label + responses: + '200': + description: User value set item updated + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + $ref: '../components/schemas/valuesets.yaml#/ValueSetItem' + + delete: + tags: [ValueSets] + summary: Delete user value set item + description: Delete value set item from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: User value set item deleted + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + +/api/valueset/user/def: + get: + tags: [ValueSets] + summary: List user value set definitions + description: List value set definitions from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: search + in: query + schema: + type: string + description: Optional search term to filter definitions + - name: page + in: query + schema: + type: integer + default: 1 + description: Page number for pagination + - name: limit + in: query + schema: + type: integer + default: 100 + description: Number of items per page + responses: + '200': + description: List of user value set definitions + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + type: array + items: + $ref: '../components/schemas/valuesets.yaml#/ValueSetDef' + meta: + type: object + properties: + total: + type: integer + page: + type: integer + limit: + type: integer + + post: + tags: [ValueSets] + summary: Create user value set definition + description: Create value set definition in database (user-defined) + security: + - bearerAuth: [] + requestBody: + required: true + content: + application/json: + schema: + type: object + properties: + SiteID: + type: integer + description: Site reference (default 1) + VSName: + type: string + description: Value set name + VSDesc: + type: string + description: Value set description + responses: + '201': + description: User value set definition created + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + $ref: '../components/schemas/valuesets.yaml#/ValueSetDef' + +/api/valueset/user/def/{id}: + get: + tags: [ValueSets] + summary: Get user value set definition by ID + description: Get value set definition from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: User value set definition details + content: + application/json: + schema: + type: object + properties: + status: + type: string + data: + $ref: '../components/schemas/valuesets.yaml#/ValueSetDef' + + put: + tags: [ValueSets] + summary: Update user value set definition + description: Update value set definition in database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + requestBody: + required: true + content: + application/json: + schema: + type: object + properties: + SiteID: + type: integer + description: Site reference + VSName: + type: string + description: Value set name + VSDesc: + type: string + description: Value set description + responses: + '200': + description: User value set definition updated + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string + data: + $ref: '../components/schemas/valuesets.yaml#/ValueSetDef' + + delete: + tags: [ValueSets] + summary: Delete user value set definition + description: Delete value set definition from database (user-defined) + security: + - bearerAuth: [] + parameters: + - name: id + in: path + required: true + schema: + type: integer + responses: + '200': + description: User value set definition deleted + content: + application/json: + schema: + type: object + properties: + status: + type: string + message: + type: string