Una página que llama a la API
Parte de la sección API REST del Journey de Node.js de Coddy. Lección 21 de 25.
Una página llama a tu API con fetch. Un POST necesita tres opciones: método, encabezados y cuerpo. Convierte el objeto JavaScript en texto JSON para el cuerpo y etiqueta ese texto como application/json.
const response = await fetch('/api/books', {
method: 'POST',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify({title: title}),
});
const data = await response.json();El primer await recibe la respuesta HTTP. El segundo lee su cuerpo JSON. response.ok te indica si su estado está dentro del rango de éxito. Un estado como 400 o 409 no rechaza la promesa de fetch; devuelve una respuesta cuyo ok es false. El código del formulario y de la lista ya está proporcionado; céntrate en enviar la solicitud y gestionar el resultado.
La variable message proporcionada hace referencia al párrafo de mensajes de la página. Asigna texto a su textContent para mostrarlo, o una cadena vacía para borrarlo:
message.textContent = data.error.message;
// Bórralo después de que se complete correctamente:
message.textContent = '';La página y la API comparten un mismo origen, así que esta llamada no necesita permiso CORS. FormData codifica un formulario de forma distinta a JSON; usa texto JSON porque esta API utiliza express.json().
Desafío
FácilTu API todavía no tiene interfaz. Añádele una página sencilla, servida por el mismo servidor, cuyo formulario agregue tareas a través de la API.
- En
server.js, sirve la carpetapublicconexpress.static, para queGET /devuelvapublic/index.html. - En
public/index.html, el listener de envío ya lee el título. Haz que envíe la nueva tarea a la API:- Usa la variable
titleproporcionada, que contiene el texto de entrada. - Envíala con
fetch('/api/tasks', ...)como una solicitud POST. - El cuerpo es texto JSON creado con
JSON.stringify, como{"title":"Water the plants"}. - La solicitud necesita el encabezado
'Content-Type': 'application/json'en la opciónheadersdefetch; de lo contrario,express.json()no leerá el cuerpo.
- Usa la variable
- Si la respuesta es correcta (su propiedad
okes true para cualquier estado entre 200 y 299), limpia el formulario conform.reset(), vacía#messagey llama aload()para que la lista muestre la nueva tarea. - De lo contrario, el cuerpo de la respuesta tiene el formato de error visto antes, por ejemplo:Muestra su
{ "error": { "code": "conflict", "message": "A task with this title already exists" } }messageen el párrafo#message.
Las comprobaciones ejecutan el script de esta página proporcionado con un pequeño formulario simulado y la API real de la lección. Envían una tarea y luego un duplicado, y después inspeccionan la lista, el formulario y el mensaje. Prueba también la página real junto al editor.
Pruébalo: envía GET /. La página se abre en la vista de página con las 3 tareas iniciales. Escribe "Water the plants" y pulsa Añadir: el campo de entrada se vacía y la tarea aparece al final de la lista. Escribe "Water the plants" de nuevo y pulsa Añadir: la lista permanece igual y aparece "A task with this title already exists" debajo del formulario.
Pruébalo tú mismo
<!doctype html>
<html lang="en">
<head>
<meta charset="utf-8">
<title>Tasks</title>
</head>
<body>
<h1>Tasks</h1>
<ul id="list"></ul>
<form id="add">
<input name="title" placeholder="New task" required>
<button>Add</button>
</form>
<p id="message"></p>
<script>
const list = document.querySelector('#list');
const form = document.querySelector('#add');
const message = document.querySelector('#message');
async function load() {
const response = await fetch('/api/tasks?limit=50');
const page = await response.json();
list.replaceChildren(...page.items.map((task) => {
const item = document.createElement('li');
item.textContent = (task.done ? '[x] ' : '[ ] ') + task.title;
return item;
}));
}
form.addEventListener('submit', async (event) => {
event.preventDefault();
const title = form.elements.title.value;
// Send the title to POST /api/tasks as JSON. On success clear
// the form and load() again; on an error show its message.
});
load();
</script>
</body>
</html>
Todas las lecciones de API REST
1Recursos y verbos
Recursos y URLCrear con POST4Navegadores, versiones y configuración
Qué es un origenPermitir otro origenCORSUna página que llama a la APIPractica por tu cuenta: Playground de Express