-
Notifications
You must be signed in to change notification settings - Fork 1
2. Frontend
Note: Run npm run dev
to generate api.ts
Types are generated when the server is running, so if a type isn't there. Edge-case; start/restart the dev server.
On the front-end you can access your api by importing it, and it will have type-safety all the way.
import api from '$src/api'
api.ts is a generated file by Zero API. It will include the type and functions for the whole operation.
If we have src/routes/api/products/+server.ts
as an endpoint with a POST, we can access it as api.products.POST
The api will automatically pick up the paramters for the endpoint.
If you await an api function such as api.products.GET()
, you will get a Response (unless you're using .$.).
let response = await api.products.GET()
if(response.status == 200)
console.log(response.body)
// eqv. to
api.products.GET().ok(r => console.log(r.body))
If you have a route like
src/routes/api/products/[warehouse]/storage/[product]/+server.ts
You can access this by using
api.products.warehouse$('austin-warehouse').storage.product$(productId).GET()
In SvelteKit, the load functions has its own fetch which you can pass to the api.
If running an api
call on the client and server, without providing a fetch function as the second argument — the api
will only be called on the client.
import type { PageLoad } from './$types'
export const load: PageLoad = async ({ params, fetch }) => {
const { id } = params
// Pass `fetch` as the second argument
const response = await api.products.id$(id).GET({}, fetch)
return {
status: response.status,
props: {
product: response.ok && response.body
}
}
}
For every response in your endpoint, there will be a callback function. If your backend returns
return Ok({ body: { message: 'Hello there' } })
Then you can access it doing:
api.product.GET().ok(response => { console.log(response.body.message) })
Every response-code has their own callback
Ok: 200 // .Ok(response => )
BadRequest: 400 // .BadRequest(response => )
InternalError: 500 // .InternalError(response => )
And some callbacks cover more:
Any: xxx // .Any(r => )
Informational: 1xx // .Informational(r => )
Success: 2xx // .Success(r => )
Redirect: 3xx // .Redirect(r => )
ClientError: 4xx // .ClientError(r => )
ServerError: 5xx // .ServerError(r => )
Error: 4xx or 5xx // .Error(r => )
if(A)
return Ok({ body: { message: 'Hello there', lol: false } })
else
return Created({ body: { message: 'Message created', product: someProduct, lol: true } })
// Side-note: Any Error response (4xx/5xx), have { error: string, target: any }
// as optional options. They will be in response: { body: { error, target } }
// If error isn't populated, the error message will be it's name f.i. "error: 'Internal Error'"
return InternalError({ error: 'Something went wrong' })
Here you'll find the types:
api.product.GET()
// { body: { message: string, lol: boolean }, ... }
.Ok(response => {
const {
message, ✅
product, ⛔
lol ✅
} = response.body
})
// { body: { message: string, product: ProductType, lol: boolean }, ... }
.Created(({ body }) => {
const {
message, ✅
product, ✅
lol ✅
} = body
})
// { body: { error: string }, ... }
.InternalError(r => console.error(r.body.error)) ✅
.Success(r => {
let body = r.body
// All Success responses have { body: { message: string } }
body.message ✅
// Not all have product
body.product ⛔
if(!('product' in body)) // Return if 'product'-key is not in body
return
// Because we checked if product is in body, it is now valid
body.product ✅
})
These functions will also be called in order. So
- Ok
- Success
or
- Created
- Success
In case of 200 (Ok) or 201 (Created)
If an endpoint does not return a status-code, but you still want a callback use ._. wildcard:
api.product.GET()._.UnavailableForLegalReasons(handleError)
An exception to getting a Promise<Response>
, is using the wildcard .$.
This returns whatever is returned from the trailing callback. Naturally, only one is allowed. And is only allowed in the end of the function.
If the return isn't an Ok
, then it returns undefined.
// products: Product[] | undefined
let products = await api.product.GET().$.Ok(r => r.body)
if(!products) {
console.error('Did not receive any products.')
return
}
import type { ResponseBody, RequestParams } from 'sveltekit-zero-api/helpers'
ResponseBody gets the body of a response, for a specific status-code.
// Where response: { body: { products: Product[] } }
let products: ResponseBody<typeof api.products.GET, 'Ok'>['products']
let productParams: RequestParams<typeof api.products.POST> = {
body: { productName: 'Banana' },
query: { value: 69.101 }
}
Installation: Get Started Firstly recommended: Backend Usage: Frontend