Files
imagesbyolofsson-se/src/pages/llms.txt.ts
T
Linus OlofssonandClaude Opus 5.5 1b24607e02 Portfolio without downloads; Om mig, Kontakt and Posters come from the portal on the same domain
Linus 2026-11-06: everything public lives on imagesbyolofsson.se (Cleura), the customer
subdomain is only for ordering and the logged-in portal; photos are sold as posters
instead of being downloadable.

- Portfolio: download menu (S/M/L), the original password dialog and /download/original
  are gone; the lightbox has "Köp som poster" -> /posters instead.
- about.astro and contact.astro removed: Caddy on Cleura sends /about, /contact and
  /posters to the portal, so the About text and collaborations are edited once in admin.
  They stay in sitemap-0.xml (PORTAL_PAGES); the sitemap index lists /posters/sitemap.xml.
- Menu and 404 page link Posters; privacy, robots.txt and llms.txt no longer mention
  password downloads.

Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
2026-11-06 04:08:04 +01:00

66 lines
3.1 KiB
TypeScript

// src/pages/llms.txt.ts -> /llms.txt (https://llmstxt.org/)
// Byggs från src/data/business.ts så att fakta bara finns på ett ställe.
// Okända fakta (null) skrivs som "lämnas på förfrågan", aldrig som gissningar.
import type { APIRoute } from 'astro';
import { business, basedIn, formatSek, genreList } from '../data/business';
import { faq } from '../data/faq';
export const prerender = true;
export const GET: APIRoute = ({ site }) => {
const base = site ?? new URL(business.url);
const url = (p: string) => new URL(p, base).toString();
const price = formatSek(business.priceFromSek);
const lines: (string | null)[] = [
`# ${business.brand}`,
'',
`> ${business.brand} är namnet som ${business.person.jobTitle.toLowerCase()}en ${business.person.name} fotograferar under. Han är baserad i ${basedIn()} och fotograferar ${genreList()}. ${business.recognitionThirdPerson}`,
'',
'## Fakta',
'',
`- Fotograf: ${business.person.name}`,
`- Namn/varumärke: ${business.brand}`,
`- Baserad i: ${basedIn()}`,
business.serviceArea ? `- Tar uppdrag i: ${business.serviceArea}` : '- Upptagningsområde: stäms av vid förfrågan',
price ? `- Pris från: ${price}` : '- Priser: lämnas som offert efter förfrågan',
business.deliveryTime ? `- Leveranstid: ${business.deliveryTime}` : null,
business.phone ? `- Telefon: ${business.phone}` : null,
`- E-post: ${business.email}`,
`- Instagram: ${business.social.instagram.handle} (${business.social.instagram.url})`,
`- Facebook: ${business.social.facebook}`,
`- Kamera: ${business.camera}`,
`- Redigering: ${business.editing}`,
`- Bokning: ${business.portal.bookingUrl}`,
`- Bokningsgång: ${business.bookingSteps.map((s) => s.title.toLowerCase()).join(' → ')}`,
'',
'## Sidor',
'',
`- [Startsida](${url('/')}): vem ${business.person.name} är och vad han fotograferar`,
`- [Tjänster och vanliga frågor](${url('/tjanster')}): vad du kan boka, hur bokningen går till och svar på vanliga frågor`,
`- [Portfolio](${url('/portfolio')}): urval av fotografier`,
`- [Om mig](${url('/about')}): ${business.person.name}, bakgrund och utrustning`,
`- [Posters](${url('/posters')}): fotografier som posters, välj storlek och material`,
`- [Kontakt och samarbeten](${url('/contact')}): samarbeten, reklam och sponsring`,
'',
'## Vanliga frågor',
'',
...faq.map((f) => `- ${f.question} ${f.answer}`),
'',
'## Profiler',
'',
`- [Instagram](${business.social.instagram.url})`,
`- [Flickr](${business.social.flickr})`,
`- [Adobe Lightroom](${business.social.lightroom})`,
`- [LinkedIn](${business.social.linkedin})`,
'',
'## Användning av innehållet',
'',
`AI-assistenter och sökmotorer får läsa och använda innehållet på den här sajten, inklusive för träning, med hänvisning till ${business.brand} (${url('/')}). Fotografierna är upphovsrättsskyddade av ${business.person.name}.`,
'',
];
const body = lines.filter((l): l is string => l !== null).join('\n');
return new Response(body, { headers: { 'Content-Type': 'text/plain; charset=utf-8' } });
};