complex-teal
complex-teal2y ago

Typing the `custom` method in DataProvider

Hello, I am trying to type the response data from my custom method in the DataProvider, which uses the generic TData to type the response. How do I define it when implementing my provider logic?
7 Replies
kapa.ai
kapa.ai2y ago
Hi @bombillazo. I'm kapa.ai, your friendly support bot. I will try to answer your question by searching through the knowledge base. :wave:
kapa.ai
kapa.ai2y ago
---------------------- To define the TData type when implementing your custom method in the DataProvider, you can use the DataProvider type from refine. Here's an example of how to do it:
import { DataProvider } from "@pankod/refine";

export const dataProvider = (apiUrl: string): DataProvider => ({
// ...
custom: async <TData>({
url,
method,
filters,
sorters,
payload,
query,
headers,
}): Promise<{ data: TData }> => {
// Your custom implementation here
},
// ...
});
import { DataProvider } from "@pankod/refine";

export const dataProvider = (apiUrl: string): DataProvider => ({
// ...
custom: async <TData>({
url,
method,
filters,
sorters,
payload,
query,
headers,
}): Promise<{ data: TData }> => {
// Your custom implementation here
},
// ...
});
In this example, the custom method is defined as an async function with a generic type parameter TData. This allows you to type the response data when using the custom method in your application. For more information on creating a custom data provider, refer to the Create Data Provider From Scratch (https://refine.dev/docs/tutorial/understanding-dataprovider/create-dataprovider/) section in the tutorial. ---------------------- Note: you can ask me a follow up question by @ mentioning me again :speech_balloon: ----------------------
kapa.ai
kapa.ai2y ago
<@260960777010151436> kapa.ai is still learning and improving, please let us how it did by reacting below
complex-teal
complex-tealOP2y ago
@kapa.ai How do I narrow the response type inside my custom function implementation to avoid type constraint errors and allow different response types depending on the input?
kapa.ai
kapa.ai2y ago
Let me check the knowledge base for you. One moment! :books:
kapa.ai
kapa.ai2y ago
---------------------- To narrow the response type inside your custom function implementation and allow different response types depending on the input, you can use TypeScript's conditional types and type inference. Here's an example of how to do it: First, define a type that maps the input to the expected response type:
type CustomResponseType<T extends string> = T extends "resourceA"
? ResourceAResponse
: T extends "resourceB"
? ResourceBResponse
: unknown;
type CustomResponseType<T extends string> = T extends "resourceA"
? ResourceAResponse
: T extends "resourceB"
? ResourceBResponse
: unknown;
In this example, ResourceAResponse and ResourceBResponse are the expected response types for resourceA and resourceB, respectively. Next, update your custom method implementation to use the CustomResponseType type:
import { DataProvider } from "@pankod/refine";

export const dataProvider = (apiUrl: string): DataProvider => {
// ...
custom: async <TResource extends string>({
resource,
// other parameters
}): Promise<{ data: CustomResponseType<TResource> }> => {
// Your custom implementation here
},
// ...
};
import { DataProvider } from "@pankod/refine";

export const dataProvider = (apiUrl: string): DataProvider => {
// ...
custom: async <TResource extends string>({
resource,
// other parameters
}): Promise<{ data: CustomResponseType<TResource> }> => {
// Your custom implementation here
},
// ...
};
Now, when you use the custom method in your application, the response type will be narrowed based on the input resource:
const { data: resourceAData } = useCustom<ResourceAResponse>({
resource: "resourceA",
// other parameters
});

const { data: resourceBData } = useCustom<ResourceBResponse>({
resource: "resourceB",
// other parameters
});
const { data: resourceAData } = useCustom<ResourceAResponse>({
resource: "resourceA",
// other parameters
});

const { data: resourceBData } = useCustom<ResourceBResponse>({
resource: "resourceB",
// other parameters
});
For more information on creating a custom data provider, refer to the Create Data Provider From Scratch (https://refine.dev/docs/tutorial/understanding-dataprovider/create-dataprovider/) section in the tutorial. ---------------------- Note: you can ask me a follow up question by @ mentioning me again :speech_balloon: ----------------------
kapa.ai
kapa.ai2y ago
<@260960777010151436> kapa.ai is still learning and improving, please let us how it did by reacting below