Aprende a cubrir la creación y actualización de posts con enfoque TDD, asegurando rutas, validaciones y estados HTTP correctos. Desde los datos mínimos del payload hasta las respuestas esperadas, aquí se explica paso a paso cómo estructurar las pruebas de post y put para garantizar calidad y claridad desde el inicio.
¿Qué se construye con TDD en la creación y actualización de posts?
Empezamos por las pruebas: una para el método post (crear) y otra para put (actualizar). Se prepara un payload con título, contenido, estado de publicación y user ID. Se aclara que “post” se refiere al método HTTP, no al modelo. Tras enviar la petición al endpoint "posts", se parsea la respuesta con json.parse sobre response.body y se validan estructura, ID y estado HTTP esperado.
Además, se explica que en describe el string es solo descriptivo del contexto del test. Para evitar confusiones entre el método post y la entidad, se usa un nombre alterno como article al preparar datos para la actualización. El flujo TDD se refuerza al ejecutar las pruebas y confirmar que inicialmente fallan por rutas inexistentes, lo cual es el resultado esperado antes de implementar la lógica.
¿Qué datos requiere el payload de creación?
Título del post.
Contenido del post.
Publicado: valor booleano.
User ID: asociado al usuario creado con let y FactoryBot.
¿Cómo se valida la respuesta del método post?
Parseo del cuerpo: json.parse sobre response.body.
Estructura: el payload no debe estar vacío.
Identidad: el payload debe contener un ID.
Estado HTTP: se espera created en lugar del número, para mayor legibilidad.
TDD: al correr pruebas, es correcto que fallen por no encontrar la ruta de "posts".
# Creaciónit 'It should create a post'do# payload con título, contenido, publicado: false, user_id. post 'posts',params: payload
parsed = json.parse(response.body) expect(parsed).not_to be_empty
expect(parsed).to include('id') expect(response).to have_http_status(:created)end
¿Cómo se prueba la actualización con put sin confusiones?
Para actualizar se necesita un post existente. Se crea con FactoryBot y, para no confundir con el método post, se nombra la variable como article. El payload de actualización puede cambiar título, contenido y publicado (por ejemplo, a true). El user ID no se actualiza. Se envía put con el ID del recurso, se parsea la respuesta y se aseguran las condiciones clave: contenido no vacío, ID igual al existente y estado HTTPok.
Al ejecutar, las pruebas deben fallar si la ruta put no existe aún. Esto confirma el ciclo TDD: primero rojo, luego la implementación.
¿Qué estados HTTP se comprueban y por qué?
Creación con post: estado created para indicar que el recurso se creó.
Actualización con put: estado ok para indicar éxito en la modificación.
Legibilidad: se pueden usar identificadores en lugar de números.
# Actualizaciónit 'actualiza el artículo existente'do# article existente put "posts/:id",params: payload_actualizado
parsed = json.parse(response.body) expect(parsed).not_to be_empty
expect(parsed['id']).to eq(article.id) expect(response).to have_http_status(:ok)end
¿Cómo se manejan errores y validaciones en creación y actualización?
Se añaden pruebas negativas para confirmar respuestas y mensajes de error. En creación, un título vacío debe devolver estado HTTPunprocessable entity, sin ID y con una llave de error no vacía. En actualización, un payload con título y contenido en nil también debe devolver unprocessable entity y un mensaje de error. Al correr el conjunto, es normal ver las cuatro pruebas fallar si aún no existen las rutas.
¿Qué habilidades y conceptos prácticos se aplican aquí?
Enfoque TDD: primero pruebas, luego implementación.
Métodos HTTPpost y put para crear y actualizar.
Estructura de payload con campos mínimos.
Parseo de JSON con json.parse y uso de response.body.
Estados HTTP: created, ok, unprocessable entity.
Manejo de rutas y verificación de fallos iniciales.
Generación de datos con FactoryBot y aleatorios con Faker.
Asserts claros con expect y descripciones con describe y string.
Claridad semántica: diferenciar el método post del modelo post usando article como nombre alterno.
¿Te gustaría compartir cómo validas tus mensajes de error o qué estrategia sigues para nombrar variables y mantener claridad entre métodos HTTP y modelos?
Si los datos que el usuario envía al endpoint el HTTP status code de respuesta no debería ser unprocessable entity sino bad request (400).
unprocessable entity se usa cuando el dato que ya está en el servidor no es valido y por alguna razón no se puede procesar.
Segun sé, el 400 se ocupa cuando el usuario envia mal los datos, por ejemplo parametros distintos, otros tipos de datos. el 422 se ocupa cuando estos datos que se enviaron, no puedes ser convertidor en data para el servidor se responde con esto.
Donde puedo encontrar más documentación sobre ese tipo de pruebas?
Espero poder ser de ayuda con lo siguiente, tome algunas preguntas como referente aunque aquí ya han respondido algunas “ej:*”:
Por dónde iniciar?
¿Qué debo probar, o como utilizar la logica de programacion para saber que se debe probar?
* ¿Qué gemas o complemento debo usar?
Cómo implementarlas las pruebas?
Algún libro recomendado sobre este tema ?
Dado que como tu, tengo el mismo interés en el tema, postee esta pregunta en
Antes que nada, este es el ciclo TDD
Algunos link de interés:
Cuando nuestro sistema es enorme, lo mejor es usar mocks y stubs para no persistir en la BD.
porque no hacer un fayload con faker como se ha venido implementando:
Me parece que para el teste de creacion no es necesario usar faker ya que solo comprobaremos que los campos no esten vacions (nil)
Para el test PUT, en la linea " let!(:article) { create(:post) }" se crea un post con ayuda de la gema Faker y luego esta actualiza con lo que se envia por paramentro
¿ por qué no se crea el request payload usando faker?