La Raya · app (6): puntos de interés — llevar al usuario hasta un dolmen sin dirección

Publicado el 08/06/2026

También creía cerrada la serie de la app. Pero el backend acababa de poblar la sección de puntos de interés —museos, dólmenes, castillos, ermitas de los dos lados de la Raya (su serie lo cuenta)— y tocaba enseñarlo. Resultó ser la entrada más corta de las dos mitades, y por una buena razón.

Casi todo el trabajo ya estaba hecho

Cuando monté la gastronomía (capítulo 5) dejé sin querer el camino allanado: la sección de turismo es su gemela. Misma estructura —pantalla con buscador y filtro por tipo, tarjetas, pantalla de detalle, navegación—, mismos componentes reutilizables. La pantalla de turismo ya existía, el cliente de API ya tenía sus métodos y el tipo PuntoTuristico ya estaba declarado. Adaptar la sección fue, sobre todo, completar un hueco concreto.

El aprendizaje del capítulo anterior, otra vez

En la entrada de gastronomía aprendí, a base de tropezar, que si el tipo de TypeScript no incluye un campo, la app lo descarta en silencio aunque el backend lo mande. Pues volvió a pasar: el endpoint de turismo ya devolvía latitud y longitud, pero el tipo PuntoTuristico no las declaraba, así que llegaban y se tiraban. Añadirlas al tipo fue el primer paso —y el más fácil de olvidar—:

export interface PuntoTuristico {
  // …
  latitud: number | null;
  longitud: number | null;
}

Tu tipo es tu contrato. Si no lo declaras, no existe.

El detalle que importa: "cómo llegar" a algo sin dirección

Aquí está la diferencia real frente a la gastronomía. Un bar tiene calle y número; un dolmen en mitad de una dehesa, o una ermita en un cerro, no tienen dirección postal. Lo único fiable que tienen son sus coordenadas —que precisamente las fuentes de patrimonio sí traen.

En el capítulo de gastronomía, "Cómo llegar" buscaba por texto (nombre + localidad). Para turismo eso te deja a las puertas del pueblo, no del monumento. Así que el botón usa las coordenadas directas cuando existen, y solo cae al texto si faltan:

const mapsUrl =
  punto.latitud != null && punto.longitud != null
    ? `https://maps.google.com/?q=${punto.latitud},${punto.longitud}`
    : `https://maps.google.com/?q=${encodeURIComponent(`${punto.title}, ${localidad}`)}`;

Un cambio pequeño con un efecto grande: la diferencia entre "te dejo en el pueblo, búscalo" y "te llevo a la piedra".

Bilingüe sin esfuerzo extra

Como el resto de la app, las descripciones llegan en el idioma elegido (ES/PT) gracias a la cabecera de idioma y a las traducciones del backend —que para turismo salen de Wikipedia y de las fichas oficiales—. La app no hace nada especial: pide en su idioma y muestra lo que recibe. La infraestructura de i18n que monté al principio sigue pagando dividendos capítulo tras capítulo.

Lo que me llevo

  • El trabajo bien hecho se hereda. Hacer la gastronomía con componentes reutilizables convirtió "montar turismo" en "rellenar un hueco". Las secciones gemelas deben compartir esqueleto.
  • Tu tipo es tu contrato (otra vez). Dos capítulos seguidos tropezando con lo mismo: un campo que el backend envía pero el tipo no declara es un campo que no existe para la app.
  • Adapta la acción al dato. "Cómo llegar" por texto vale para un bar; para un dolmen necesitas coordenadas. La misma función, decidida por lo que cada sitio tiene de verdad.
  • La i18n bien puesta no se vuelve a tocar. Pedir en el idioma del usuario y confiar en el backend hizo que la sección naciera bilingüe sin una línea extra.

Y ahora sí, con la frontera llena de patrimonio y la app llevándote hasta su puerta, cierro otra vez la serie. A ver cuánto dura el cierre esta vez.