v0.17.0 Release
⚠️ Please read carefully the release notes as there are some minor breaking changes!
-
To simplify file uploads, we now allow sending the
multipart/form-data
request body also as plain object if at least one of the object props hasFile
orBlob
value.// the standard way to create multipart/form-data body const data = new FormData(); data.set("title", "lorem ipsum...") data.set("document", new File(...)) // this is the same as above // (it will be converted behind the scenes to FormData) const data = { "title": "lorem ipsum...", "document": new File(...), }; await pb.collection("example").create(data);
-
Added new
pb.authStore.isAdmin
andpb.authStore.isAuthRecord
helpers to check the type of the current auth state. -
The default
LocalAuthStore
now listen to the browser storage event,
so that we can sync automatically thepb.authStore
state between multiple tabs. -
Added new helper
AsyncAuthStore
class that can be used to integrate with any 3rd party async storage implementation (usually this is needed when working with React Native):import AsyncStorage from "@react-native-async-storage/async-storage"; import PocketBase, { AsyncAuthStore } from "pocketbase"; const store = new AsyncAuthStore({ save: async (serialized) => AsyncStorage.setItem("pb_auth", serialized), initial: await AsyncStorage.getItem("pb_auth"), }); const pb = new PocketBase("https://example.com", store)
-
pb.files.getUrl()
now returns empty string in case an empty filename is passed. -
⚠️ All API actions now return plain object (POJO) as response, aka. the custom class wrapping was removed and you no longer need to manually callstructuredClone(response)
when using with SSR frameworks.This could be a breaking change if you use the below classes (and respectively their helper methods like
$isNew
,$load()
, etc.) since they were replaced with plain TS interfaces:class BaseModel -> interface BaseModel class Admin -> interface AdminModel class Record -> interface RecordModel class LogRequest -> interface LogRequestModel class ExternalAuth -> interface ExternalAuthModel class Collection -> interface CollectionModel class SchemaField -> interface SchemaField class ListResult -> interface ListResult
Side-note: If you use somewhere in your code the
Record
andAdmin
classes to determine the type of yourpb.authStore.model
,
you can safely replace it with the newpb.authStore.isAdmin
andpb.authStore.isAuthRecord
getters. -
⚠️ Added support for per-requestfetch
options, including also specifying completely customfetch
implementation.In addition to the default
fetch
options, the following configurable fields are supported:interface SendOptions extends RequestInit { // any other custom key will be merged with the query parameters // for backward compatibility and to minimize the verbosity [key: string]: any; // optional custom fetch function to use for sending the request fetch?: (url: RequestInfo | URL, config?: RequestInit) => Promise<Response>; // custom headers to send with the requests headers?: { [key: string]: string }; // the body of the request (serialized automatically for json requests) body?: any; // query params that will be appended to the request url query?: { [key: string]: any }; // the request identifier that can be used to cancel pending requests requestKey?: string|null; // @deprecated use `requestKey:string` instead $cancelKey?: string; // @deprecated use `requestKey:null` instead $autoCancel?: boolean; }
For most users the above will not be a breaking change since there are available function overloads (when possible) to preserve the old behavior, but you can get a warning message in the console to update to the new format.
For example:// OLD (should still work but with a warning in the console) await pb.collection("example").authRefresh({}, { "expand": "someRelField", }) // NEW await pb.collection("example").authRefresh({ "expand": "someRelField", // send some additional header "headers": { "X-Custom-Header": "123", }, "cache": "no-store" // also usually used by frameworks like Next.js })
-
Eagerly open the default OAuth2 signin popup in case no custom
urlCallback
is provided as a workaround for Safari. -
Internal refactoring (updated dev dependencies, refactored the tests to use Vitest instead of Mocha, etc.).