From da4eda535893f1a26b095e5890658099e89d9457 Mon Sep 17 00:00:00 2001 From: "(quasar) nebula" Date: Mon, 6 Mar 2023 10:27:40 -0400 Subject: data-steps: initial commit --- src/page/album.js | 184 ++++++++++++++++++++++++++++++++++++++---------------- src/page/index.js | 70 +++++++++++++++++++++ 2 files changed, 200 insertions(+), 54 deletions(-) (limited to 'src/page') diff --git a/src/page/album.js b/src/page/album.js index 9ee57c0..a266b91 100644 --- a/src/page/album.js +++ b/src/page/album.js @@ -12,55 +12,148 @@ import { getTotalDuration, } from '../util/wiki-data.js'; +import { + generateContributionLinks as u_generateContributionLinks, +} from '../misc-templates.js'; + +import u_link from '../util/link.js'; + export const description = `per-album info & track artwork gallery pages`; export function targets({wikiData}) { return wikiData.albumData; } -export function write(album, {wikiData}) { - const unbound_trackToListItem = (track, { - getArtistString, - getLinkThemeString, - html, - language, - link, - }) => { - const itemOpts = { - duration: language.formatDuration(track.duration ?? 0), - track: link.track(track), - }; +export const dataSteps = { + computePathsForTarget(data, album) { + data.hasGalleryPage = album.tracks.some(t => t.hasUniqueCoverArt); + data.hasCommentaryPage = !!album.commentary || album.tracks.some(t => t.commentary);; - return html.tag('li', - {style: getLinkThemeString(track.color)}, - compareArrays( - track.artistContribs.map((c) => c.who), - album.artistContribs.map((c) => c.who), - {checkOrder: false} - ) - ? language.$('trackList.item.withDuration', itemOpts) - : language.$('trackList.item.withDuration.withArtists', { - ...itemOpts, - by: html.tag('span', - {class: 'by'}, - language.$('trackList.item.withArtists.by', { - artists: getArtistString(track.artistContribs), - })), - })); + return [ + { + type: 'page', + path: ['album', album.directory], + }, + + data.hasGalleryPage && { + type: 'page', + path: ['albumGallery', album.directory], + }, + + data.hasCommentaryPage && { + type: 'page', + path: ['albumCommentary', album.directory], + }, + + { + type: 'data', + path: ['album', album.directory], + }, + ]; + }, + + computeDataCommonAcrossMixedWrites(data, album) { + data.albumDuration = getTotalDuration(album.tracks); + }, + + computeDataCommonAcrossPageWrites(data, album) { + data.listTag = getAlbumListTag(album); + }, + + computeDataForPageWrite: { + album(data, album, _pathArgs) { + data.hasAdditionalFiles = !empty(album.additionalFiles); + data.numAdditionalFiles = album.additionalFiles.flatMap((g) => g.files).length; + + data.displayTrackSections = + album.trackSections && + (album.trackSections.length > 1 || + !album.trackSections[0]?.isDefaultTrackSection); + }, + }, + + computeContentForPageWrite: { + album(data, { + absoluteTo, + fancifyURL, + generateAdditionalFilesShortcut, + generateAdditionalFilesList, + generateChronologyLinks, + generateContributionLinks, + generateContentHeading, + generateNavigationLinks, + getAlbumCover, + getAlbumStylesheet, + getLinkThemeString, + getSizeOfAdditionalFile, + getThemeString, + html, + link, + language, + transformMultiline, + urls, + }) { + const generateTrackListItem = bindOpts(u_generateTrackListItem, { + generateContributionLinks, + getLinkThemeString, + html, + language, + link, + }); + + void generateTrackListItem; + }, + }, +}; + +function u_generateTrackListItem(data, { + generateContributionLinks, + getLinkThemeString, + html, + language, + link, +}) { + const stringOpts = { + duration: language.formatDuration(data.duration), + track: link.track(data.linkData), }; - const hasAdditionalFiles = !empty(album.additionalFiles); - const numAdditionalFiles = album.additionalFiles.flatMap((g) => g.files).length; + return html.tag('li', + {style: getLinkThemeString(data.color)}, + (!data.showArtists + ? language.$('trackList.item.withDuration', stringOpts) + : language.$('trackList.item.withDuration.withArtists', { + ...stringOpts, + by: + html.tag('span', {class: 'by'}, + language.$('trackList.item.withArtists.by', { + artists: generateContributionLinks(data.contributionLinksData), + })), + }))); +} - const albumDuration = getTotalDuration(album.tracks); +u_generateTrackListItem.data = track => { + return { + color: track.color, + duration: track.duration ?? 0, + linkData: u_link.track.data(track), - const displayTrackSections = - album.trackSections && - (album.trackSections.length > 1 || - !album.trackSections[0]?.isDefaultTrackSection); + showArtists: + !compareArrays( + track.artistContribs.map((c) => c.who), + track.album.artistContribs.map((c) => c.who), + {checkOrder: false}), - const listTag = getAlbumListTag(album); + contributionLinksData: + u_generateContributionLinks.data(track.artistContribs, { + showContribution: false, + showIcons: false, + }), + }; +}; +/* +export function write(album, {wikiData}) { const getSocialEmbedDescription = ({ getArtistString: _getArtistString, language, @@ -127,24 +220,6 @@ export function write(album, {wikiData}) { type: 'page', path: ['album', album.directory], page: ({ - absoluteTo, - fancifyURL, - generateAdditionalFilesShortcut, - generateAdditionalFilesList, - generateChronologyLinks, - generateContentHeading, - generateNavigationLinks, - getAlbumCover, - getAlbumStylesheet, - getArtistString, - getLinkThemeString, - getSizeOfAdditionalFile, - getThemeString, - html, - link, - language, - transformMultiline, - urls, }) => { const trackToListItem = bindOpts(unbound_trackToListItem, { getArtistString, @@ -867,3 +942,4 @@ export function generateAlbumAdditionalFilesList(album, additionalFiles, { link.albumAdditionalFile({album, file}), }); } +*/ diff --git a/src/page/index.js b/src/page/index.js index f580cbe..fc0c646 100644 --- a/src/page/index.js +++ b/src/page/index.js @@ -17,6 +17,76 @@ // Usually this will simply mean returning the appropriate thingData array, // but it may also apply filter/map/etc if useful. // +// dataSteps {...} +// Object with key-to-functions matching a variety of steps described next. +// In general, the use of dataSteps is to separate data computations from +// actual page content generation, making explicit what data is carried +// from one step to the next, and letting the build/serve mode have a +// standardized guideline for deciding when to compute data at each step. +// +// Important notes on the usage of dataSteps: +// +// - Every dataStep function is provided a `data` object which stores +// values passed through to that step. To save data for a coming step, +// just mutate this object (set a key and value on it). +// +// - Some dataStep functions return values, but not all do. Some are just +// for computing data used by following steps. +// +// - Do not set any data properties to live wiki objects or arrays/objects +// including live wiki objects. All data passed between each step should +// be fully serializable in JSON or otherwise plain-text format. +// +// **NB: DATA WRITES ARE CURRENTLY DISABLED. All steps exclusively applicable +// to data writes will currently be skipped.** +// +// dataSteps.computePathsForTargets(data, target) +// Compute paths at which pages or files will be generated for the given +// target wiki object, returning {type, path} pairs. Data applied here, +// such as flags indicating which pages have content, will automatically +// be passed onto all further steps. +// +// dataSteps.computeDataCommonAcrossMixedWrites(data, target) +// Compute data which is useful in a mixed list of any path writes. +// This function should only be used when data is pertinent to more than +// one kind of write, ex. a variable which is useful for page writes but +// also exposed through a data write. Data applied here is passed onto +// all further steps. +// +// dataSteps.computeDataCommonAcrossPageWrites(data, target) +// Compute data which is useful across more than one page write. +// Use this function when data is pertinent to more than one page write, +// but isn't relevant outside of page writes. Data applied here is passed +// onto further steps for page writes. +// +// dataSteps.computeDataCommonAcrossDataWrites(data, target) +// Analagous to computeDataAcrossPages; for data writes. +// +// dataSteps.computeDataForPageWrite.[pathKey](data, target, pathArgs) +// Compute data which is useful for a single given page write. +// Note that dataSteps.computeDataForPage is an object; its keys are the +// possible path keys from computePathsForTargets() for page writes. +// Data applied here is passed onto the final write call for this page. +// +// dataSteps.computeDataForDataWrite.[pathKey](data, target, pathArgs) +// Analogous to computeDataForPageWrite; for data writes. +// +// dataSteps.computeContentForPageWrite.[pathKey](data, utils) +// Use data prepared in previous steps to compute and return the actual +// content for a given page write. The target wiki object is no longer +// accessible at this step, so all required data must be computed ahead. +// +// - The returned page object will be destructured for +// usage in generateDocumentHTML(), `src/write/page-template.js`. +// +// - The utils object is a set of bound functions handy for any page +// content. It is described in `src/write/bind-utilities.js`. +// +// dataSteps.compteContentForDataWrite.[pathKey](data, utils) +// Analogous to computeContentForDataWrite; for data writes. +// NB: When data writes are enabled, the utils object will be uniquely +// defined separate from what's provided to page writes. +// // write(thing, {wikiData}) // Provides descriptors for any page and data writes associated with the // given thing (which will be a value from the targets() array). This -- cgit 1.3.0-6-gf8a5