pocketbase/ui/src/utils/ApiClient.js

124 lines
3.1 KiB
JavaScript
Raw Normal View History

import PocketBase, { LocalAuthStore, Admin, isTokenExpired } from "pocketbase";
2022-07-07 05:19:05 +08:00
// ---
import CommonHelper from "@/utils/CommonHelper";
import { replace } from "svelte-spa-router";
import { addErrorToast } from "@/stores/toasts";
import { setErrors } from "@/stores/errors";
import { setAdmin } from "@/stores/admin";
const adminFileTokenKey = "pb_admin_file_token";
2022-07-07 05:19:05 +08:00
/**
* Clears the authorized state and redirects to the login page.
*
* @param {Boolean} [redirect] Whether to redirect to the login page.
*/
PocketBase.prototype.logout = function(redirect = true) {
2022-08-02 22:00:14 +08:00
this.authStore.clear();
2022-07-07 05:19:05 +08:00
if (redirect) {
replace('/login');
}
};
/**
* Generic API error response handler.
*
* @param {Error} err The API error itself.
* @param {Boolean} notify Whether to add a toast notification.
* @param {String} defaultMsg Default toast notification message if the error doesn't have one.
*/
PocketBase.prototype.errorResponseHandler = function(err, notify = true, defaultMsg = '') {
if (!err || !(err instanceof Error) || err.isAbort) {
2022-07-07 05:19:05 +08:00
return;
}
const statusCode = (err?.status << 0) || 400;
const responseData = err?.data || {};
2022-07-07 05:19:05 +08:00
// add toast error notification
if (
notify && // notifications are enabled
statusCode !== 404 // is not 404
) {
let msg = responseData.message || err.message || defaultMsg;
if (msg) {
addErrorToast(msg);
}
}
// populate form field errors
if (!CommonHelper.isEmpty(responseData.data)) {
setErrors(responseData.data);
}
// unauthorized
if (statusCode === 401) {
this.cancelAllRequests();
return this.logout();
}
// forbidden
if (statusCode === 403) {
this.cancelAllRequests();
return replace('/');
}
};
/**
* @return {Promise<String>}
*/
PocketBase.prototype.getAdminFileToken = async function() {
let token = localStorage.getItem(adminFileTokenKey) || '';
// request a new token only if the previous one is missing or will expire soon
if (!token || isTokenExpired(token, 15)) {
// remove previously stored token (if any)
token && localStorage.removeItem(adminFileTokenKey);
if (!this._adminFileTokenRequest) {
this._adminFileTokenRequest = this.files.getToken();
}
token = await this._adminFileTokenRequest;
localStorage.setItem(adminFileTokenKey, token);
this._adminFileTokenRequest = null;
}
return token;
}
2022-07-07 05:19:05 +08:00
// Custom auth store to sync the svelte admin store state with the authorized admin instance.
class AppAuthStore extends LocalAuthStore {
/**
* @inheritdoc
*/
save(token, model) {
super.save(token, model);
if (model instanceof Admin) {
setAdmin(model);
}
}
/**
* @inheritdoc
*/
clear() {
super.clear();
2022-08-02 22:00:14 +08:00
2022-07-07 05:19:05 +08:00
setAdmin(null);
}
}
const client = new PocketBase(
import.meta.env.PB_BACKEND_URL,
new AppAuthStore("pb_admin_auth")
);
2022-08-02 22:00:14 +08:00
if (client.authStore.model instanceof Admin) {
setAdmin(client.authStore.model);
2022-07-07 05:19:05 +08:00
}
export default client;