Use a custom icon library for pre made edit, show, delete button

Hi, I would like to switch the icon of the premade refine icons to use @tabler/icons-react instead
16 Replies
kapa.ai
kapa.ai6mo ago
Hi @blackbearftw. I'm kapa.ai, your friendly support bot. I will try to answer your question by searching through the knowledge base. :wave: ---------------------- To customize the icons of the pre-made buttons in Refine, you can use the swizzle command provided by Refine's CLI. This command allows you to export the components of the UI integrations and use them in your application. You can then modify these components at a granular level to fit your needs. Here's how you can use the swizzle command:
npm run refine swizzle
npm run refine swizzle
You'll be prompted to select the package and the component you want to swizzle. For example, if you want to customize the <EditButton />, you can select it from the list. Once you've swizzled the component, you can modify its code to use the @tabler/icons-react library for the icons. Please note that swizzling is a one-time operation and it may be hard to maintain the changes and keep track of the new features in the future. Swizzling a component will detach it from the related package and it will be your responsibility to keep it up to date. For more information about the swizzle command, you can check out the CLI documentation (https://refine.dev/docs/packages/list-of-packages/). Also, remember that Refine comes with Ant Design System, which provides a collection of free icons. If you want to use these icons, you can pass them to the icon prop of the button components. For more information about customizing the components, you can check out the UI Libraries Customization guide (https://refine.dev/docs/guides-concepts/ui-libraries#customization) in the Refine documentation. ---------------------- Note: you can ask me a follow up question by @ mentioning me again :speech_balloon: ----------------------
kapa.ai
kapa.ai6mo ago
<@490961337896402944> kapa.ai is still learning and improving, please let us know how it did by reacting below
fascinating-indigo
fascinating-indigo6mo ago
Does this actually work? @kapa.ai does this actually work, also won't this just stop the entire refine package from being updated?
kapa.ai
kapa.ai6mo ago
Let me check the knowledge base for you. One moment! :books: ---------------------- Yes, the swizzle command does work and allows you to customize the components of Refine. However, it's important to note that swizzling is a one-time operation. Once you swizzle a component, it will be detached from the related package and it will be your responsibility to keep it up to date. This means that if the original component in the Refine package gets updated, your swizzled component won't receive those updates automatically. You'll need to manually update your swizzled component to incorporate any changes made in the original component. That being said, swizzling a component doesn't stop the entire Refine package from being updated. The rest of the package will continue to receive updates as usual. Only the swizzled component will be detached from the package. Here's an example of how you can use the swizzle command:
npm run refine swizzle
npm run refine swizzle
After running this command, you'll be prompted to select the package and the component you want to swizzle. Once you've swizzled the component, you can modify its code to fit your needs. For more information about the swizzle command, you can check out the CLI documentation (https://refine.dev/docs/packages/list-of-packages/). For more information about customizing the components, you can check out the UI Libraries Customization guide (https://refine.dev/docs/guides-concepts/ui-libraries#customization) in the Refine documentation. ---------------------- Note: you can ask me a follow up question by @ mentioning me again :speech_balloon: ----------------------
kapa.ai
kapa.ai6mo ago
<@490961337896402944> kapa.ai is still learning and improving, please let us know how it did by reacting below
fascinating-indigo
fascinating-indigo6mo ago
@kapa.ai unrelated question, how could I add teams or groups of users that all have access to the same content.
kapa.ai
kapa.ai6mo ago
Let me check the knowledge base for you. One moment! :books: ---------------------- To implement teams or groups of users that all have access to the same content, you would need to implement a form of access control in your application. Refine provides an agnostic API via the accessControlProvider to manage access control throughout your app. An accessControlProvider must implement only one async method named can to be used to check if the desired access will be granted. You can use this method to check if a user belongs to a certain team or group and grant access based on that. Here's an example of how you can use the accessControlProvider:
const accessControlProvider: AccessControlProvider = {
can: async ({ role, resource, action, params, record }) => {
// Check if the user's role has access to the resource
if (role === 'admin') {
return true;
}

// Check if the user belongs to a certain team or group
if (team.includes(user)) {
return true;
}

return false;
},
};
const accessControlProvider: AccessControlProvider = {
can: async ({ role, resource, action, params, record }) => {
// Check if the user's role has access to the resource
if (role === 'admin') {
return true;
}

// Check if the user belongs to a certain team or group
if (team.includes(user)) {
return true;
}

return false;
},
};
In this example, the can method checks if the user's role is 'admin' or if the user belongs to a certain team. If either of these conditions is true, the method returns true, granting access to the user. For more detailed information and a step-by-step guide, you can check out the Access Control Provider documentation (https://refine.dev/docs/core/providers/access-control-provider/). Please note that the actual implementation of teams or groups of users would depend on your backend. You would need to have a way to assign users to teams or groups and check these assignments in your accessControlProvider. For more advanced solutions, you can integrate different methods (RBAC, ABAC, ACL, etc.) and different libraries (Casbin (https://casbin.org/), CASL (https://casl.js.org/v5/en/), Cerbos (https://cerbos.dev/), AccessControl.js (https://onury.io/accesscontrol/)) as mentioned in the Access Control Introduction (https://refine.dev/docs/advanced-tutorials/access-control#introduction). ---------------------- Note: you can ask me a follow up question by @ mentioning me again :speech_balloon: ----------------------
kapa.ai
kapa.ai6mo ago
<@490961337896402944> kapa.ai is still learning and improving, please let us know how it did by reacting below
fascinating-indigo
fascinating-indigo6mo ago
@kapa.ai how would I use refine.js with asp.net core web api
kapa.ai
kapa.ai6mo ago
Let me check the knowledge base for you. One moment! :books: ---------------------- To use Refine with an ASP.NET Core Web API, you would need to set up a data provider that communicates with your API. Refine provides a set of data providers for some common backends, but you can also create a custom data provider for your specific needs. Here's a basic example of how you can create a custom data provider:
import { fetchUtils } from "@pankod/refine";

const dataProvider = {
getList: async (resource, params) => {
const { url, options } = fetchUtils.fetchJson(
`<https://my-api.com/${resource}`,>
{
method: "GET",
}
);

const { json } = await fetchUtils.fetchJson(url, options);

return {
data: json.items,
total: json.total,
};
},
// Implement other methods like getOne, getMany, etc.
};

export default dataProvider;
import { fetchUtils } from "@pankod/refine";

const dataProvider = {
getList: async (resource, params) => {
const { url, options } = fetchUtils.fetchJson(
`<https://my-api.com/${resource}`,>
{
method: "GET",
}
);

const { json } = await fetchUtils.fetchJson(url, options);

return {
data: json.items,
total: json.total,
};
},
// Implement other methods like getOne, getMany, etc.
};

export default dataProvider;
In this example, the getList method sends a GET request to your API and returns the data and the total number of items. You would need to implement similar methods for other actions like getOne, getMany, create, update, delete, etc. Once you've created your data provider, you can pass it to the Refine component in your app:
import dataProvider from "./dataProvider";

const App = () => (
<Refine dataProvider={dataProvider}>
{/* ... */}
</Refine>
);
import dataProvider from "./dataProvider";

const App = () => (
<Refine dataProvider={dataProvider}>
{/* ... */}
</Refine>
);
Please note that the actual implementation of your data provider would depend on the specifics of your ASP.NET Core Web API. You would need to adjust the URLs, request methods, headers, and other parameters to match your API. For more detailed information and a step-by-step guide, you can check out the Data Provider documentation (https://refine.dev/docs/core/providers/data-provider/). ---------------------- Note: you can ask me a follow up question by @ mentioning me again :speech_balloon: ----------------------
kapa.ai
kapa.ai6mo ago
<@490961337896402944> kapa.ai is still learning and improving, please let us know how it did by reacting below
fascinating-indigo
fascinating-indigo6mo ago
@kapa.ai but my api is protected with jwt tokens from keycloak
kapa.ai
kapa.ai6mo ago
Let me check the knowledge base for you. One moment! :books: ---------------------- To use JWT tokens from Keycloak with your ASP.NET Core Web API, you would need to set up an authProvider in Refine. The authProvider is responsible for handling authentication in your application. It includes methods for logging in, logging out, checking for authentication, and getting authentication parameters. Here's a basic example of how you can create an authProvider:
const authProvider = {
login: async ({ username, password }) => {
const { data } = await axios.post('<https://my-api.com/auth/login',> {
username,
password,
});

localStorage.setItem('token', data.token);
},
logout: () => {
localStorage.removeItem('token');
},
checkError: () => Promise.resolve(),
checkAuth: () => localStorage.getItem('token')
? Promise.resolve()
: Promise.reject(),
getPermissions: () => Promise.resolve(),
getIdentity: () => Promise.resolve(),
};

export default authProvider;
const authProvider = {
login: async ({ username, password }) => {
const { data } = await axios.post('<https://my-api.com/auth/login',> {
username,
password,
});

localStorage.setItem('token', data.token);
},
logout: () => {
localStorage.removeItem('token');
},
checkError: () => Promise.resolve(),
checkAuth: () => localStorage.getItem('token')
? Promise.resolve()
: Promise.reject(),
getPermissions: () => Promise.resolve(),
getIdentity: () => Promise.resolve(),
};

export default authProvider;
In this example, the login method sends a POST request to your API's login endpoint and stores the returned token in local storage. The logout method removes the token from local storage. The checkAuth method checks if a token exists in local storage. Once you've created your authProvider, you can pass it to the Refine component in your app:
import authProvider from "./authProvider";

const App = () => (
<Refine authProvider={authProvider}>
{/* ... */}
</Refine>
);
import authProvider from "./authProvider";

const App = () => (
<Refine authProvider={authProvider}>
{/* ... */}
</Refine>
);
Please note that the actual implementation of your authProvider would depend on the specifics of your Keycloak setup and your ASP.NET Core Web API. You would need to adjust the URLs, request methods, headers, and other parameters to match your API and Keycloak setup. For more detailed information and a step-by-step guide, you can check out the Auth Provider documentation (https://refine.dev/docs/core/providers/auth-provider/). To pass the JWT token to your API with each request, you can use Axios interceptors in your data provider. Here's an example:
axiosInstance.interceptors.request.use((request) => {
const token = localStorage.getItem('token');
if (token) {
request.headers["Authorization"] = `Bearer ${token}`;
}
return request;
});
axiosInstance.interceptors.request.use((request) => {
const token = localStorage.getItem('token');
if (token) {
request.headers["Authorization"] = `Bearer ${token}`;
}
return request;
});
In this example, an interceptor is added to the Axios instance that adds the Authorization header with the JWT token to each request. For more information on how to use Keycloak JWT with the DataProvider and Axios in Refine, you can refer to this Github Issue (https://github.com/refinedev/refine/issues/4908). ---------------------- Note: you can ask me a follow up question by @ mentioning me again :speech_balloon: ----------------------
kapa.ai
kapa.ai6mo ago
<@490961337896402944> kapa.ai is still learning and improving, please let us know how it did by reacting below
fascinating-indigo
fascinating-indigo6mo ago
@kapa.ai How do I use a custom color for mantine theme in refine?
kapa.ai
kapa.ai6mo ago
Let me check the knowledge base for you. One moment! :books: @blackbearftw That's a great question, but unfortunately I am only capable of responding to a maximum of five questions per thread. Don't hesitate to create a new thread for any further questions you have though. I'm here to help!