Description
Feature request
add an unwrap()
method or a an either monad left()
method to pull the data out of a postgrest response.
Is your feature request related to a problem? Please describe.
Not exactly a problem, but the way the client is designed requires every database query to individually handle database failures. For the most part, I want to assume that the query succeeded, and throw an error if it did not. That makes most of my db calls look like this:
const res = await context.supabase
.from<tables['my_table']>('my_table')
.select()
.filter('status', 'eq', 'COMPLETED')
.limit(1)
if (res.error) throw new Error(`SupabaseError: query failed: \n${res.error}`)
Describe the solution you'd like
The solution I would like best, would be to add a method which can optionally unwrap the { error: object } | { data: object[] }
response from supabase into just the data field. If there is an error present, the client should throw an error. This should not break any existing workflows, its just an optional convenience method.
Usage:
const data: table['my_table'] = await supabase.from<table['my_table']>('my_table')
.select()
.unwrap()
// handling an error:
try {
const data = await supabase.from('my_table').delete().unwrap()
} catch (e) {
if (e.name === 'SupabaseError') {
// handle it
} else {
throw e
}
}
Describe alternatives you've considered
I have attempted building this on top of the supabase client, but because of the way queries are built, I need to use proxies:
const supabase_proxy_handler = {
get: function (target: any, prop: string) {
if (prop === 'unwrap') {
return new Promise((resolve, reject) => {
target.then((res: PostgrestResponse) => {
if (res.error) throw new Error(`SupabaseError: query failed: \n${JSON.stringify(res.error)}`)
else return res.data
})
})
} else {
return target[prop]
}
},
}
const supabase_proxy = new Proxy(supabase, supabase_proxy_handler)
This technically works, but manipulating the types to include the unwrap()
method is harder.
Additional context
unwrap
is a common pattern in several languages & libraries. Here is an example in rust: https://doc.rust-lang.org/rust-by-example/error/option_unwrap.html