{"id":19664278,"url":"https://github.com/beda-software/aidbox-react","last_synced_at":"2025-11-07T07:02:31.566Z","repository":{"id":42240611,"uuid":"195450238","full_name":"beda-software/aidbox-react","owner":"beda-software","description":"A set of TypeScript components and utilities to create react apps on top of AidBox ","archived":false,"fork":false,"pushed_at":"2025-05-21T09:44:50.000Z","size":479,"stargazers_count":10,"open_issues_count":18,"forks_count":8,"subscribers_count":10,"default_branch":"master","last_synced_at":"2025-06-13T17:07:58.728Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"TypeScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/beda-software.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","contributing":null,"funding":null,"license":"LICENSE.md","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null,"zenodo":null}},"created_at":"2019-07-05T18:08:07.000Z","updated_at":"2025-05-21T09:44:51.000Z","dependencies_parsed_at":"2025-04-28T21:38:44.575Z","dependency_job_id":"ffc167c2-b7a9-45c3-a215-aca71b9200ce","html_url":"https://github.com/beda-software/aidbox-react","commit_stats":null,"previous_names":[],"tags_count":5,"template":false,"template_full_name":null,"purl":"pkg:github/beda-software/aidbox-react","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/beda-software%2Faidbox-react","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/beda-software%2Faidbox-react/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/beda-software%2Faidbox-react/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/beda-software%2Faidbox-react/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/beda-software","download_url":"https://codeload.github.com/beda-software/aidbox-react/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/beda-software%2Faidbox-react/sbom","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":266067293,"owners_count":23871328,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":[],"created_at":"2024-11-11T16:17:20.313Z","updated_at":"2025-11-07T07:02:26.530Z","avatar_url":"https://github.com/beda-software.png","language":"TypeScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# aidbox-react\n\n[![Build Status](https://travis-ci.org/beda-software/aidbox-react.svg?branch=master)](https://travis-ci.org/beda-software/aidbox-react) [![Coverage Status](https://coveralls.io/repos/github/beda-software/aidbox-react/badge.svg?branch=master)](https://coveralls.io/github/beda-software/aidbox-react?branch=master)\n\nTypeScript library consisting of set of utils, functions and [React hooks](https://reactjs.org/docs/hooks-intro.html) to work with Aidbox's [FHIR API](http://hl7.org/fhir/). Based on [axios](https://github.com/axios/axios).\n\nSo basically it is a javascript/typescript Aidbox FHIR-client.\nThe main difference between FHIR and Aidbox data structure in our case is Reference's format. Aidbox uses two separate fields: `resourceType` and `id` while FHIR uses `resourceType/id`. [Read more](https://docs.aidbox.app/basic-concepts/aidbox-and-fhir-formats)\n\n# Install\n\nClone this repository into `src/contrib/aidbox-react`\nand provide type definitions for aidbox in `src/contrib/aidbox` (see example/basic set of [Aidbox typings](https://github.com/beda-software/aidbox-react/blob/master/typings/contrib/aidbox.d.ts))\n\n# Introduction\n\n## RemoteData\n[RemoteData](https://github.com/beda-software/aidbox-react/blob/master/src/libs/remoteData.ts) is a wrapper over data.\n\nIt could have four statuses:\n* Success\n* Failure\n* Loading\n* NotAsked\n\nRemoteDataResult is a subset of RemoteData and it could have two statuses:\n* Success\n* Failure\n\nWhen we make a request to a server with any of library's methods, we'll probably get RemoteData as a result. Then we can easily check what've got.\n\n\u003cdetails\u003e\n\u003csummary\u003eSimplified example\u003c/summary\u003e\n\n```TypeScript\nimport React from 'react';\n// Your Aidbox typings. Read above in Install section of this Readme\nimport { Patient } from 'contrib/aidbox';  \nimport { getFHIRResource } from 'aidbox-react/lib/services/fhir';\nimport { isFailure, isSuccess } from 'aidbox-react/lib/libs/remoteData';\n\nasync function loadPatientGender() {\n    const patientResponse = await getFHIRResource\u003cPatient\u003e({\n        resourceType: 'Patient',\n        id: 'patient-id',\n    });\n    if (isSuccess(patientResponse)) {\n        return `Patient name is ${patientResponse.data.gender ?? 'unknown'}`;\n    }\n    if (isFailure(patientResponse)) {\n        return `\n            Failed to request patient,\n            status: ${patientResponse.status},\n            error : ${patientResponse.error}\n        `;\n    }\n}\n```\n\u003c/details\u003e\n\n##\n# Content\n\nWe consider service as a function that returns `RemoteDataResult\u003cS, F\u003e` (`RemoteDataSuccess\u003cS\u003e | RemoteDataSuccess\u003cF\u003e`). For details, see `RemoteData` interface in `aidbox-react/libs/remoteData.ts`\n\n## Available functions (services)\n\n-   service({...axiosConfig})\n-   FHIR-specific:\n    -   getFHIRResource(reference)\n    -   getFHIRResources(resourceType, params)\n    -   getAllFHIRResources(resourceType, params)\n    -   findFHIRResource(resourceType, params)\n    -   saveFHIRResource(resource)\n    -   createFHIRResource(resource)\n    -   updateFHIRResource(resource, params)\n    -   patchFHIRResource(resource, params)\n    -   saveFHIRResources(resources, bundleType)\n    -   deleteFHIRResource(resources)\n    -   forceDeleteFHIRResource(resource)\n\n### service({...axiosConfig})\nBasic function for making requests.\n\n```TypeScript\nimport { service } from 'aidbox-react/lib/services/service';\nimport { formatError } from 'aidbox-react/lib/utils/error';\nimport { isFailure, isSuccess } from 'aidbox-react/lib/libs/remoteData';\n\nasync function deleteAccount() {\n    const result = await service({\n        url: '/User/$delete-account',\n        method: 'POST',\n    });\n    if (isSuccess(result)) {\n        await logout();\n    } else if (isFailure(result)) {\n        console.error(formatError(result.error));\n    }\n}\n```\n\n### getFHIRResource\nGet resource by reference (resource type and id).\n\n```TypeScript\nimport { getFHIRResource } from 'aidbox-react/lib/services/fhir';\n// ...\n\nconst observationResponse = await getFHIRResource\u003cObservation\u003e(makeReference('Observation', 'observation-id'));\n```\n\n### getFHIRResources\nGet resources using [Search API](https://www.hl7.org/fhir/search.html)\nReturns only first page of resources.\n\n```TypeScript\nimport { getFHIRResources } from 'aidbox-react/lib/services/fhir';\n// ...\n\nconst qrBundleResponse = await getFHIRResources\u003cQuestionnaireResponse\u003e('QuestionnaireResponse', {\n    subject: subject.id,\n    questionnaire: 'intake',\n    status: 'completed',\n});\nif (isSuccess(qrBundleResponse)) {\n    // Iterate over found resources\n    qrBundleResponse.data.entry?.forEach((bundleEntry) =\u003e {\n        console.log(bundleEntry.resource?.status);\n    });\n}\n```\n\n### getAllFHIRResources\nGet all found resources from all pages.\n\n```TypeScript\nimport moment from 'moment';\nimport { getAllFHIRResources } from 'aidbox-react/lib/services/fhir';\nimport { formatFHIRDateTime } from 'aidbox-react/lib/utils/date';\n// ...\n\nconst observationsResponse = await getAllFHIRResources\u003cObservation\u003e('Observation', {\n    _sort: '-date',\n    _count: 500,\n    patient: 'patient-id',\n    status: 'final',\n    date: [`ge${formatFHIRDateTime(moment())}`],\n});\n```\n\n### findFHIRResource\nUses [Search API](https://www.hl7.org/fhir/search.html) to find exactly one resource and return in (not bundle). It throws `Error('Too many resources found')` if more than one resources were found and `Error('No resources found')` if nothing were found.\n\n\u003c!-- TODO: Add try/catch example? --\u003e\n```TypeScript\nimport { findFHIRResource } from 'aidbox-react/lib/services/fhir';\n\nconst roleResponse = await findFHIRResource\u003cPractitionerRole\u003e('PractitionerRole', {\n    practitioner: 'practitioner-id',\n});\n```\n\n### saveFHIRResource\nSaves resource. If resource has `id` – uses `PUT` method (updates), otherwise `POST` (creates).\nIf you want to have more control, you can use `createFHIRResource` or `updateFHIRResource` functions.\n\n```TypeScript\nimport { saveFHIRResource } from 'aidbox-react/lib/services/fhir';\n// ...\n\nconst saveResponse = await saveFHIRResource({\n    resourceType: 'Patient',\n    gender: 'female',\n});\n\nif (isFailure(saveResponse)) {\n    console.warn('Can not create a patient: ', JSON.stringify(saveResponse.error));\n}\n```\n\n### createFHIRResource(resource)\nCreates resource via `POST` command.\nThe difference with `saveFHIRResource` is that `createFHIRResource` always use `POST`, even if resource has `id` field.\n\n```TypeScript\nconst resource = {\n    id: '1',\n    resourceType: 'Patient',\n};\n\nawait createFHIRResource(resource);\n```\n\n### updateFHIRResource(resource, params)\nUpdates resource using `PUT` request.\n\nIt's required to have either resource's id or pass `params`.\n\n```TypeScript\nconst resource = {\n    resourceType: 'Patient',\n    name: [{text: 'Alex'}]\n};\nconst searchParams = { identifier: 'alex-1' };\n\nconst updateResponse = await updateFHIRResource(resource, searchParams);\n```\n\n### patchFHIRResource(resource, params)\nUse `PATCH` method to patch a resource.\n\nIt's required to have either resource's id or pass `params`.\n\n```TypeScript\nconst resource = {\n    resourceType: 'Patient',\n    name: [{text: 'Jennifer'}],\n    gender: 'female'\n};\n\nconst createResponse = await createFHIRResource(resource);\nif (isSuccess(createResponse)) {\n    const patchResponse = await patchFHIRResource({\n        id: createResponse.data.id,\n        name: [{text: 'Monica'}]\n    });\n}\n```\n\n### saveFHIRResources(resources, bundleType)\nSave an array of resources using `POST` request.\n\nMethod for every resource will be either `PUT` (if resource's id presented) or\n\n```TypeScript\nconst bundleResponse = await saveFHIRResources([\n    {\n        id: 'jennifer-1',\n        resourceType: 'Patient',\n        name: [{text: 'Jennifer'}]\n    },\n    {\n        resourceType: 'Patient',\n        name: [{text: 'Monica'}]\n    }\n], 'transaction');\n```\n\n### deleteFHIRResource(resources)\nActually it doesn't delete a resource, just mark it as deleted by altering its status (see `inactiveMapping` list in `fhir.ts`).\n\n```TypeScript\nawait deleteFHIRResource(makeReference('Patient', 'patient-id'));\n```\n\n### forceDeleteFHIRResource(resource)\nDeletes resource by calling `DELETE` method.\n\n```TypeScript\nconst createResponse = await createFHIRResource({\n    resourceType: 'Patient',\n    name: [{text: 'Max'}]\n});\nif (isSuccess(createResponse)) {\n    const deleteResource = await forceDeleteFHIRResource(makeReference('Patient', createResponse.data.id));\n}\n```\n\n## Available hooks\n\n-   useService(serviceFn)\n-   usePager(resourceType, resourcesOnPage?, searchParams?)\n-   useCRUD(resourceType, id?, getOrCreate?, defaultResource?) - WIP\n\n# Usage\n\nSet baseURL and token for axios instance using `setInstanceBaseURL` and `setInstanceToken/resetInstanceToken` from `aidbox-react/services/instance`\nAnd use hooks and services\n\n# Examples\n\n## Pager hook\n\n```TSX\nimport * as React from 'react';\n\nimport { User } from 'shared/src/contrib/aidbox';\nimport { usePager } from 'src/contrib/aidbox-react/services/service';\nimport { isLoading, isSuccess } from 'src/contrib/aidbox-react/libs/remoteData';\nimport { extractBundleResources } from 'src/contrib/aidbox-react/services/fhir';\n\nexport function UserList(props: {}) {\n    const [resourcesResponse, pagerManager] = usePager\u003cUser\u003e('User', 2);\n\n    if (isLoading(resourcesResponse)) {\n        return \u003cdiv\u003eLoading...\u003c/div\u003e;\n    }\n\n    if (isSuccess(resourcesResponse)) {\n        const users = extractBundleResources(resourcesResponse.data).User || [];\n\n        return (\n            \u003cdiv\u003e\n                \u003ca onClick={() =\u003e pagerManager.loadNext()}\u003eLoad next\u003c/a\u003e\n\n                {users.map((user) =\u003e (\n                    \u003cdiv key={user.id}\u003e{user.id}\u003c/div\u003e\n                ))}\n            \u003c/div\u003e\n        );\n    }\n\n    return null;\n}\n```\n\n## CRUD hook\n\n```TSX\nimport * as React from 'react';\n\nimport { useCRUD } from 'src/contrib/aidbox-react/hooks/crud';\nimport { isLoading, isSuccess } from 'src/contrib/aidbox-react/libs/remoteData';\nimport { Patient } from 'shared/src/contrib/aidbox';\n\nexport function UserList(props: {}) {\n    const [resourceResponse, crudManager] = useCRUD\u003cPatient\u003e('Patient', 'toggle', true, {\n        resourceType: 'Patient',\n        active: false,\n    });\n\n    if (isLoading(resourceResponse)) {\n        return \u003cdiv\u003eLoading...\u003c/div\u003e;\n    }\n\n    if (isSuccess(resourceResponse)) {\n        // This is just an example\n        const active = resourceResponse.data.active;\n\n        return (\n            \u003cdiv\u003e\n                Active: {active ? 'Yes' : 'No'}\n                \u003ca\n                    onClick={() =\u003e\n                        crudManager.handleSave({\n                            ...resourceResponse.data,\n                            active: !active,\n                        })\n                    }\n                \u003e\n                    Toggle\n                \u003c/a\u003e\n            \u003c/div\u003e\n        );\n    }\n    return null;\n}\n```\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbeda-software%2Faidbox-react","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fbeda-software%2Faidbox-react","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fbeda-software%2Faidbox-react/lists"}