* Make /db top-level module * Create Album type * Pin pnpm version * Generalize query modules * Finalize album postgres data type * Remove temp albums prop * Create basic album primitives * Fix temporary album bugs * Add albums to sidebar * Disambiguate string date utilities * Localize album language * Add album join option to core photo queries * Tweak album icon placement * Add album photo detail page * Refine Album data model * Display album subhead when available * Generate album og images * Finalize album share modal * Add albums to sitemap * Statically pre-render albums * Display tags on albums * Add albums to cmd-k menu * Handle album tag overflow * Stop truncating album subheads * Create core admin album views * Make albums editable * Create/edit albums on photo save, add delete album
151 lines
4.0 KiB
TypeScript
151 lines
4.0 KiB
TypeScript
import type { MetadataRoute } from 'next';
|
|
import { getDataForCategoriesCached } from '@/category/cache';
|
|
import {
|
|
ABSOLUTE_PATH_FULL,
|
|
ABSOLUTE_PATH_GRID,
|
|
absolutePathForAlbum,
|
|
absolutePathForCamera,
|
|
absolutePathForFilm,
|
|
absolutePathForFocalLength,
|
|
absolutePathForLens,
|
|
absolutePathForPhoto,
|
|
absolutePathForRecents,
|
|
absolutePathForRecipe,
|
|
absolutePathForTag,
|
|
absolutePathForYear,
|
|
} from '@/app/path';
|
|
import { isTagFavs } from '@/tag';
|
|
import { BASE_URL, GRID_HOMEPAGE_ENABLED } from '@/app/config';
|
|
import { getPhotoIdsAndUpdatedAt } from '@/photo/query';
|
|
|
|
// Cache for 24 hours
|
|
export const revalidate = 86_400;
|
|
|
|
const PRIORITY_HOME = 1;
|
|
const PRIORITY_HOME_VIEW = 0.9;
|
|
const PRIORITY_CATEGORY_SPECIAL = 0.8;
|
|
const PRIORITY_CATEGORY = 0.7;
|
|
const PRIORITY_PHOTO = 0.5;
|
|
|
|
export default async function sitemap(): Promise<MetadataRoute.Sitemap> {
|
|
const [
|
|
{
|
|
recents,
|
|
years,
|
|
cameras,
|
|
lenses,
|
|
albums,
|
|
tags,
|
|
recipes,
|
|
films,
|
|
focalLengths,
|
|
},
|
|
photos,
|
|
] = await Promise.all([
|
|
getDataForCategoriesCached().catch(() => ({
|
|
recents: [],
|
|
years: [],
|
|
cameras: [],
|
|
lenses: [],
|
|
albums: [],
|
|
tags: [],
|
|
recipes: [],
|
|
films: [],
|
|
focalLengths: [],
|
|
})),
|
|
getPhotoIdsAndUpdatedAt().catch(() => []),
|
|
]);
|
|
|
|
const lastModifiedSite = [
|
|
...recents.map(({ lastModified }) => lastModified),
|
|
...years.map(({ lastModified }) => lastModified),
|
|
...cameras.map(({ lastModified }) => lastModified),
|
|
...lenses.map(({ lastModified }) => lastModified),
|
|
...albums.map(({ lastModified }) => lastModified),
|
|
...tags.map(({ lastModified }) => lastModified),
|
|
...recipes.map(({ lastModified }) => lastModified),
|
|
...films.map(({ lastModified }) => lastModified),
|
|
...focalLengths.map(({ lastModified }) => lastModified),
|
|
...photos.map(({ updatedAt }) => updatedAt),
|
|
]
|
|
.filter(date => date instanceof Date)
|
|
.sort((a, b) => b.getTime() - a.getTime())[0];
|
|
|
|
return [
|
|
// Homepage
|
|
{
|
|
url: BASE_URL!,
|
|
priority: PRIORITY_HOME,
|
|
lastModified: lastModifiedSite,
|
|
},
|
|
// Grid or full
|
|
{
|
|
url: GRID_HOMEPAGE_ENABLED ? ABSOLUTE_PATH_FULL : ABSOLUTE_PATH_GRID,
|
|
priority: PRIORITY_HOME_VIEW,
|
|
lastModified: lastModifiedSite,
|
|
},
|
|
// Recents
|
|
...recents.map(({ lastModified }) => ({
|
|
url: absolutePathForRecents(),
|
|
priority: PRIORITY_CATEGORY,
|
|
lastModified,
|
|
})),
|
|
// Years
|
|
...years.map(({ year, lastModified }) => ({
|
|
url: absolutePathForYear(year),
|
|
priority: PRIORITY_CATEGORY,
|
|
lastModified,
|
|
})),
|
|
// Cameras
|
|
...cameras.map(({ camera, lastModified }) => ({
|
|
url: absolutePathForCamera(camera),
|
|
priority: PRIORITY_CATEGORY,
|
|
lastModified,
|
|
})),
|
|
// Lenses
|
|
...lenses.map(({ lens, lastModified }) => ({
|
|
url: absolutePathForLens(lens),
|
|
priority: PRIORITY_CATEGORY,
|
|
lastModified,
|
|
})),
|
|
// Albums
|
|
...albums.map(({ album, lastModified }) => ({
|
|
url: absolutePathForAlbum(album),
|
|
priority: PRIORITY_CATEGORY,
|
|
lastModified,
|
|
})),
|
|
// Tags
|
|
...tags.map(({ tag, lastModified }) => ({
|
|
url: absolutePathForTag(tag),
|
|
priority: isTagFavs(tag)
|
|
? PRIORITY_CATEGORY_SPECIAL
|
|
: PRIORITY_CATEGORY,
|
|
lastModified,
|
|
})),
|
|
// Recipes
|
|
...recipes.map(({ recipe, lastModified }) => ({
|
|
url: absolutePathForRecipe(recipe),
|
|
priority: PRIORITY_CATEGORY,
|
|
lastModified,
|
|
})),
|
|
// Films
|
|
...films.map(({ film, lastModified }) => ({
|
|
url: absolutePathForFilm(film),
|
|
priority: PRIORITY_CATEGORY,
|
|
lastModified,
|
|
})),
|
|
// Focal Lengths
|
|
...focalLengths.map(({ focal, lastModified }) => ({
|
|
url: absolutePathForFocalLength(focal),
|
|
priority: PRIORITY_CATEGORY,
|
|
lastModified,
|
|
})),
|
|
// Photos
|
|
...photos.map(({ id, updatedAt }) => ({
|
|
url: absolutePathForPhoto({ photo: id }),
|
|
priority: PRIORITY_PHOTO,
|
|
lastModified: updatedAt,
|
|
})),
|
|
];
|
|
}
|