UNPKG

@bapp/auto-api-client

Version:

Client to consume BAPP auto API, based on content types with type inference

229 lines (160 loc) 7.25 kB
# @bapp/auto-api-client Generic API to request data from and trigger actions in the Bapp API. ## Roadmap - [x] Functions for the generic endpoints - [ ] Generate Zod schemas for client-side validation - [ ] Type inference for filters, payload and response ## Installation Install the package using one of the following commands: ```sh npm i @bapp/auto-api-client axios yarn add @bapp/auto-api-client axios pnpm i @bapp/auto-api-client axios ``` Optionally, install `@tanstack/react-query` for query option getters: ```sh npm i @tanstack/react-query yarn add @tanstack/react-query pnpm i @tanstack/react-query ``` ## Types ### Type generation The package includes a bin script to generate the types from a host. Rerun it everytime you want to sync client types with server types. At the moment it only generates types for `contentType` and `taskCode`. Use it by running: ```sh npx auto-api-client <API_HOST> <path/to/generated/file.ts> yarn auto-api-client <API_HOST> <path/to/generated/file.ts> pnpm auto-api-client <API_HOST> <path/to/generated/file.ts> ``` **Example:** `npx auto-api-client https://panel.bapp.ro/api src/auto-api-generated.ts` ### Registering types Add the following somewhere in your project, ideally before the place where you instantiate `BappAutoApi`. ```ts import { Mapping } from "./auto-api-generated"; declare module "@bapp/auto-api-client" { interface Register { mapping: Mapping; } } ``` ## API ### Core #### BappAutoApi methods Name|Interface|Description -|-|- getMe|`(options) => Me`|Gets current user's profile getApp|`(appSlug, options) => App`|Gets app config from slug getEntityListIntrospect|`(contentType, options) => ListIntrospect`|Gets entity list introspect based on contentType getEntityDetailIntrospect|`(contentType, pk?, options) => DetailIntrospect`|Gets entity detail introspect based on contentType listEntities|`(contentType, options) => PagedResponse`| Gets entity list based on contentType getEntity|`(contentType, pk, options) => Entity`|Gets specific entity based on contentType and pk createEntity|`(contentType, payload, options) => Entity`|Cretes entity based on contentType updateEntity|`(contentType, pk, payload, options) => Entity`|Updates specific entity based on contentType and pk updatePartialEntity|`(contentType, pk, payload, options) => Entity`|Updates specific fields of an entity based on contentType and pk deleteEntity|`(contentType, pk, options) => Entity`|Deletes specific entity based on contentType and pk listTasks|`(options) => string[]`|Gets list of task codes detailTask|`(code, options) => TaskConfig`|Gets the config of a task runTask|`(code, payload, options) => TaskResponse`|Runs a task and returns the response listWidgets|`(code, options) => string[]`|Gets list of widget codes detailWidget|`(code, options) => WidgetConfig`|Gets the config of a widget renderWidget|`(code, payload, options) => WidgetData`|Requests a widget render and gets the render data to show #### Components Name|Interface|Description -|-|- BappAutoApiConfigProvider|`(props: HookRequestConfig) => React.ReactNode`|Provides values for the useBappAutoApiConfig hook, useful for providing `tenantId`, `appSlug` or for changing the `BappAutoApi` instance used for making requests #### Hooks Name|Interface|Description -|-|- useBappAutoApiConfig|`() => HookRequestConfig`|Gets current hook request config, it contains the current `BappAutoApi` instance, `tenantId` and `appSlug` #### Utils Name|Interface|Description -|-|- getPageParam|`(url) => number \| undefined`|Gets and parses `page` query param out of url from `next`/`previous` field of PagedResponse ### React Query #### Option getters Name|Interface -|- getMeQueryOptions|`(options) => QueryOptions` getAppQueryOptions|`(appSlug, options) => QueryOptions` getEntityListIntrospectQueryOptions|`(contentType, options)=> QueryOptions` getEntityDetailIntrospectQueryOptions|`(contentType, pk?, options) => QueryOptions` getEntityListQueryOptions|`(contentType, options) => QueryOptions` getEntityInfiniteListQueryOptions|`(contentType, options) => InfiniteQueryOptions` getEntityDetailQueryOptions|`(contentType, pk, options) => QueryOptions` getTaskListQueryOptions|`(options) => QueryOptions` getTaskDetailQueryOptions|`(code, options) => QueryOptions` getTaskRunQueryOptions|`(code, payload, options) => QueryOptions` getWidgetListQueryOptions|`(options) => QueryOptions` getWidgetDetailQueryOptions|`(code, options) => QueryOptions` getWidgetRenderQueryOptions|`(code, payload, options) => QueryOptions` ## Using another host ```js import _axios from "axios"; const axios = _axios.create({ baseURL: /* API Host here */ }); const bappAutoApi = new BappAutoApi({ axiosInstance: axios }); ``` ## Authentication Authentication can be done through axios options or interceptors. ### Using axios initial options ```js import _axios from "axios"; const axios = _axios.create({ baseURL: /* API Host here */, headers: { Authorization: `Token ${/* Static token here */}` } }); const bappAutoApi = new BappAutoApi({ axiosInstance: axios }); ``` ### Using axios interceptors ```js const bappAutoApi = new BappAutoApi({ axiosInstance: axios }); bappAutoApi.axiosInstance.interceptors.request.use(async (config) => { const token = await getToken(); if (!token) return config; config.headers.set( "Authorization", `Bearer ${token}` ); return config; }) ``` ## Using the provider The provider is useful for changing part or all of the config used to make requests. It can be used to change the `tenantId` or `appSlug` for part of the React component tree. If you are correctly passing the config to TanStack Query getters using `useBappAutoApiConfig`, then you can just add the provider somewhere above the component with the query to change how the request is being done. **Example:** ```jsx <BappAutoApiConfigProvider bappAutoApi={bappAutoApi} tenantId="37" appSlug="erp"> {children} </BappAutoApiConfigProvider> ``` ## Integrating with TanStack Router To integreat with TanStack Router, you can use the TanStack Router context API to provide the bappAutoApiConfig, then using it through `Route.useRouteContext()` or passing it to the `BappAutoApiProvider` and using it with `useBappAutoApiConfig()`. More documentation on this topic is to come. ## Example usage ### Vanilla ```ts import BappAutoApi, { getEntityListQueryOptions } from "@bapp/auto-api-client"; import { Mapping } from "./auto-api-generated"; declare module "@bapp/auto-api-client" { interface Register { mapping: Mapping; } } const bappAutoApi = new BappAutoApi(); // Defaults to https://panels.bapp.ro/api bappAutoApi.listEntities("core.country", { filter: { someQueryParam: "value" }, }); ``` ### React w/ TanStack Query It is recommened to use this with the `BappAutoApiConfigProvider`, see [Using the provider](#using-the-provider). ```js import { getEntityListQueryOptions, useBappAutoApiConfig, } from "@bapp/auto-api-client"; const bappAutoApiConfig = useBappAutoApiConfig(); const listQuery = useQuery({ ...getEntityListQueryOptions(contentType, { config: bappAutoConfig, filter: { someQueryParam: "value" }, })}, // Other query options ); ```