diff --git a/app/docs/md/conventions/head.md b/app/docs/md/conventions/head.md index 66b5c0b0..693d01ff 100644 --- a/app/docs/md/conventions/head.md +++ b/app/docs/md/conventions/head.md @@ -22,7 +22,7 @@ You can customize the contents of the Head component by editing the included `ap -```js +```javascript import { getStyles } from '@enhance/arc-plugin-styles' const { linkTag } = getStyles diff --git a/app/docs/md/routing/api-routes/index.md b/app/docs/md/routing/api-routes/index.md index 68ed9d18..be52e0da 100644 --- a/app/docs/md/routing/api-routes/index.md +++ b/app/docs/md/routing/api-routes/index.md @@ -33,7 +33,7 @@ export async function get (req) { Given a corresponding `app/pages/index.html`, any Enhance Element rendered on that page will have access to the `favorites` array via [`state.store`](/docs/elements/state/store). For example: -```js +```javascript export default function MyFavorites ({ html, state }) { const { store } = state const { favorites } = store @@ -76,3 +76,73 @@ API routes always return a `response` object: | `headers` | `object` | Set response headers as key/value pairs | `session` | `object` | Writes passed object to the session +## Requesting data on the client + +Web components can be progressively enhanced to avoid full page reloads when requesting data from an Enhance backend. Here is an example of using `fetch` in the browser to make that request. + +```javascript +const response = await fetch('/', { + headers: { 'accept': 'application/json' }, + method: 'get' +}) + +const json = await res.json() +// json: { favorites: ['coffee crisp', 'smarties'] } +``` + +## Sending data from the client + +Data can also be posted to Enhance backends via the client to avoid full page reloads. + +In order to send data to an Enhance back end, you must properly set the `Content-Type` and `accept` headers. The `Content-Type` header informs the API route about the type of data that’s being sent, while the `accept` header instructs the API route as to what type of data to return. + +### Sending JSON data + +```javascript +const response = await fetch('/', { + headers: { + 'accept': 'application/json' + 'content-type': 'application/json' + }, + method: 'post', + body: JSON.stringify({ + favourite: 'crispy crunch' + }) +}) +``` + +### Sending form data + +When sending form data, you have a couple of options. Deciding which option to use is up to you and what your backend supports. If your data schema is complex (i.e. arrays and nested objects) you may want to rely on the `@begin/validator` package to convert form encoding to JSON and validating it against your schema. For flat data structures you may want to default to sending JSON from the client. + +The first is using [`URLSearchParams`](https://developer.mozilla.org/en-US/docs/Web/API/URLSearchParams) to send data using the content type `application/x-url-form-encoded`. + +```javascript +const form = document.querySelector('form') +const response = await fetch('/', { + headers: { + 'accept': 'application/json' + 'content-type': 'application/x-url-form-encoded' + }, + method: 'post', + body: new URLSearchParams(new FormData(form)) +}) +``` + +The second option is converting your form data to JSON and sending it along as the content type of `application/json`. + +```javascript +const form = document.querySelector('form') +const response = await fetch('/', { + headers: { + 'accept': 'application/json' + 'content-type': 'application/json' + }, + method: 'post', + body: JSON.stringify( + Object.fromEntries( + new FormData(form) + ) + ) +}) +```