Skip to content

Commit

Permalink
Group showmap days into groups of 5. Remove overengineered weekkey ge…
Browse files Browse the repository at this point in the history
…neration.
  • Loading branch information
kovipu committed Apr 10, 2024
1 parent deb30e7 commit aa6e11d
Show file tree
Hide file tree
Showing 7 changed files with 79 additions and 115 deletions.
17 changes: 12 additions & 5 deletions archiver/archive.ts
Original file line number Diff line number Diff line change
@@ -1,16 +1,23 @@
import {
Show,
Showlist,
ShowsByDate,
showsToGroups,
} from '@/scripts/google/showlistHelpers';

const showlistBaseUrl = process.env.ARCHIVE_SOURCE_URL;
const emptyResponse = { showsByDate: [], weekKeys: {} } as const;
const emptyResponse = {} as const;

interface LegacyShowList {
showsByDate: ShowsByDate;
weekKeys: Record<string, string[]>;
}

/**
* Archive S3 bucket API
*/
export const fetchArchivedShowlist = async (showlistId: string) => {
export const fetchArchivedShowlist = async (
showlistId: string
): Promise<ShowsByDate> => {
if (!showlistBaseUrl) {
console.error('Arkiston polkua ei ole määritetty');
return emptyResponse;
Expand All @@ -19,13 +26,13 @@ export const fetchArchivedShowlist = async (showlistId: string) => {

try {
const response = await fetch(url);
const showlist: Show[] | Showlist = await response.json();
const showlist: Show[] | LegacyShowList = await response.json();

if (Array.isArray(showlist)) {
return showsToGroups(showlist);
}
if (showlist?.showsByDate) {
return showlist;
return showlist.showsByDate;
}
return emptyResponse;
} catch (error) {
Expand Down
28 changes: 7 additions & 21 deletions components/showlist.tsx
Original file line number Diff line number Diff line change
@@ -1,19 +1,16 @@
import { useState } from 'react';

import { useViewport } from '@/hooks/useViewport';
import { Show } from '@/scripts/google/showlistHelpers';
import { Show, ShowsByDate } from '@/scripts/google/showlistHelpers';
import { ModeButton } from './button';
import ResponsiveShowlist from './responsiveShowlist';
import ShowlistMap from './showlistMap';

interface ShowlistProps {
showsByDate: {
[key: string]: Show[];
};
weekKeys: Record<string, string[]>;
showsByDate: ShowsByDate;
}

export const Showlist = ({ showsByDate, weekKeys }: ShowlistProps) => {
export const Showlist = ({ showsByDate }: ShowlistProps) => {
const [mode, setMode] = useState<'list' | 'map'>('list');

const { isDesktop } = useViewport();
Expand All @@ -39,28 +36,17 @@ export const Showlist = ({ showsByDate, weekKeys }: ShowlistProps) => {
</div>
)}
</div>
<ShowlistSelector
showsByDate={showsByDate}
weekKeys={weekKeys}
mode={mode}
/>
<ShowlistSelector showsByDate={showsByDate} mode={mode} />
</div>
);
};

interface ShowlistSelectorProps {
showsByDate: {
[key: string]: Show[];
};
weekKeys: Record<string, string[]>;
showsByDate: ShowsByDate;
mode: 'list' | 'map';
}

const ShowlistSelector = ({
showsByDate,
weekKeys,
mode,
}: ShowlistSelectorProps) => {
const ShowlistSelector = ({ showsByDate, mode }: ShowlistSelectorProps) => {
const { isDesktop } = useViewport();

if (!isDesktop) {
Expand All @@ -71,7 +57,7 @@ const ShowlistSelector = ({
case 'list':
return <ResponsiveShowlist showsByDate={showsByDate} />;
case 'map':
return <ShowlistMap showsByDate={showsByDate} weekKeys={weekKeys} />;
return <ShowlistMap showsByDate={showsByDate} />;
}
};

Expand Down
61 changes: 40 additions & 21 deletions components/showlistMap.tsx
Original file line number Diff line number Diff line change
@@ -1,25 +1,39 @@
import { useState } from 'react';
import { differenceInMinutes, format, parse } from 'date-fns';
import fi from 'date-fns/locale/fi';
import { head, keys } from 'ramda';
import { append, head, keys, last } from 'ramda';

import { Show } from '@/scripts/google/showlistHelpers';
import { Show, ShowsByDate } from '@/scripts/google/showlistHelpers';
import { ModeButton } from './button';
import { ShowCard } from './showcard';
import { WideScreencard } from './widescreen-card';

const GROUP_SIZE = 5;

interface ShowlistMapProps {
showsByDate: Record<string, Show[]>;
weekKeys: Record<string, string[]>;
showsByDate: ShowsByDate;
}

export const ShowlistMap = ({ showsByDate, weekKeys }: ShowlistMapProps) => {
const weeks = keys(weekKeys);
export const ShowlistMap = ({ showsByDate }: ShowlistMapProps) => {
// Take every n consecutive days.
const groups: string[][] = keys(showsByDate).reduce((acc, date, idx) => {
const groupIdx = Math.floor(idx / GROUP_SIZE);
acc[groupIdx] = append(date, acc[groupIdx] ?? []);
return acc;
}, []);

const [selectedShow, setSelectedShow] = useState<Show | null>(null);
const [openWeek, setOpenWeek] = useState<string | null>(head(weeks));
const [openGroup, setOpenGroup] = useState(0);

const openWeekDays = groups[openGroup];

const openWeekDays = weekKeys[openWeek] ?? [];
const formatGroupButtonText = (group: string[]): string => {
if (group.length === 1) return formatDayKey(head(group));

const startDay = formatDayKey(head(group), 'EEEEEE dd.');
const endDay = formatDayKey(last(group));
return `${startDay}${endDay}`;
};

// prettier-ignore
const timeStamps: string[] = ['00', '01', '02', '03', '04', '05', '06', '07', '08', '09', '10', '11',
Expand All @@ -35,16 +49,18 @@ export const ShowlistMap = ({ showsByDate, weekKeys }: ShowlistMapProps) => {
forceOpen={true}
/>
)}
<div className="flex space-x-2 p-6">
{weeks.map((n, i) => (
<ModeButton
key={n + i}
text={'Viikko ' + n}
onClick={() => setOpenWeek(n)}
isActive={openWeek === n}
/>
))}
</div>
{groups.length > 1 ? (
<div className="flex space-x-2 p-6">
{groups.map((group, idx) => (
<ModeButton
key={head(group)}
text={formatGroupButtonText(group)}
onClick={() => setOpenGroup(idx)}
isActive={openGroup === idx}
/>
))}
</div>
) : null}
<div className="flex">
<div className="-mt-3 p-6">
{timeStamps.map((timeStamp, i) => (
Expand All @@ -61,9 +77,7 @@ export const ShowlistMap = ({ showsByDate, weekKeys }: ShowlistMapProps) => {
className="flex w-full max-w-[1/7] flex-col text-center"
>
<p className="mx-auto w-full font-bold text-white">
{format(parse(day, 'y.M.dd', new Date()), 'EEEEEE dd.M.', {
locale: fi,
})}
{formatDayKey(day)}
</p>

{/* If the first show of the day does not start at midnight, add buffer */}
Expand Down Expand Up @@ -94,6 +108,11 @@ export const ShowlistMap = ({ showsByDate, weekKeys }: ShowlistMapProps) => {
);
};

const formatDayKey = (day: string, format_: string = 'EEEEEE dd.M.'): string =>
format(parse(day, 'y.M.dd', new Date()), format_, {
locale: fi,
});

// If the first show of the day does not start at midnight, add buffer
const Buffer = ({ firstShow, day }: { firstShow: Show; day: string }) => {
const dayParsed = parse(day, 'y.M.dd', new Date());
Expand Down
9 changes: 2 additions & 7 deletions pages/arkisto/[showlistId].tsx
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,6 @@ interface ShowListPageProps {
showsByDate: {
[key: string]: Show[];
};
weekKeys: Record<string, string[]>;
heroImage: {
url?: string;
};
Expand All @@ -37,7 +36,6 @@ export const ShowListPage: NextPage<ShowListPageProps> = ({
name,
showsByDate,
heroImage,
weekKeys,
navigationItems,
heroSubtext,
}) => {
Expand Down Expand Up @@ -69,7 +67,7 @@ export const ShowListPage: NextPage<ShowListPageProps> = ({
</a>
</Link>
</div>
<Showlist showsByDate={showsByDate} weekKeys={weekKeys} />
<Showlist showsByDate={showsByDate} />
</div>
);
};
Expand Down Expand Up @@ -103,9 +101,7 @@ export const getStaticProps: GetStaticProps = async (context) => {
const { name, id, heroImage, heroSubtext } =
data.programmeCollection.items[0];

const { showsByDate, weekKeys } = await fetchArchivedShowlist(
currentShowlistId
);
const showsByDate = await fetchArchivedShowlist(currentShowlistId);

const navigationItems = await fetchNavigationItems();

Expand All @@ -114,7 +110,6 @@ export const getStaticProps: GetStaticProps = async (context) => {
name,
id,
showsByDate,
weekKeys,
navigationItems,
heroImage,
heroSubtext,
Expand Down
21 changes: 9 additions & 12 deletions pages/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ import {
import { contentfulImageLoader } from '@/contentful/contentfulImageLoader';
import { IndexDocument, IndexQuery } from '@/contentful/graphql/index.graphql';
import { fetchShowlist } from '@/scripts/google/client';
import { Show } from '@/scripts/google/showlistHelpers';
import { Show, ShowsByDate } from '@/scripts/google/showlistHelpers';

const isPlayerLive = process.env.NEXT_PUBLIC_PLAYER_MODE === 'live';

Expand All @@ -33,8 +33,7 @@ interface IndexProps {
heroButtonText: string;
heroButtonLink: string;
navigationItems: NavigationItem[];
showsByDate: Record<string, Show[]>;
weekKeys: Record<string, string[]>;
showsByDate: ShowsByDate;
firstDecorativeImage: {
url?: string;
width?: number;
Expand Down Expand Up @@ -64,12 +63,11 @@ const Index: NextPage<IndexProps & PlayerControls> = ({
heroButtonLink,
navigationItems,
showsByDate,
weekKeys,
firstDecorativeImage,
secondDecorativeImage,
firstContent,
secondContent,
thirdContent,
// firstDecorativeImage,
// secondDecorativeImage,
// firstContent,
// secondContent,
// thirdContent,
sponsors,
playing,
onPlayPause,
Expand Down Expand Up @@ -106,7 +104,7 @@ const Index: NextPage<IndexProps & PlayerControls> = ({
/>
)}

<Showlist showsByDate={showsByDate} weekKeys={weekKeys} />
<Showlist showsByDate={showsByDate} />

{/* First section */}
{/* <main className="flex flex-wrap-reverse items-center justify-center py-4 md:py-8"> */}
Expand Down Expand Up @@ -175,7 +173,7 @@ export const getStaticProps: GetStaticProps<IndexProps> = async () => {

const navigationItems = await fetchNavigationItems();

const { showsByDate, weekKeys } = await fetchShowlist();
const showsByDate = await fetchShowlist();

return {
props: {
Expand All @@ -186,7 +184,6 @@ export const getStaticProps: GetStaticProps<IndexProps> = async () => {
heroButtonLink,
navigationItems,
showsByDate,
weekKeys,
firstDecorativeImage,
secondDecorativeImage,
firstContent,
Expand Down
9 changes: 3 additions & 6 deletions scripts/google/client.ts
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
import { Color, Show, Showlist, showsToGroups } from './showlistHelpers';
import { Color, Show, ShowsByDate, showsToGroups } from './showlistHelpers';
import { sheets_v4 } from '@googleapis/sheets';
import { addMilliseconds, formatISO, getHours } from 'date-fns';

Expand Down Expand Up @@ -116,17 +116,14 @@ export const parseSheetToShowList = async (
return showList;
};

export const fetchShowlist = async (): Promise<Showlist> => {
export const fetchShowlist = async (): Promise<ShowsByDate> => {
const data = await getSheet({
apiKey: process.env.GA_API_KEY,
spreadsheetId: process.env.GA_SPREADSHEET_SHOWLIST,
range: process.env.GA_SPREADSHEET_RANGE,
});
if (!data) {
return {
showsByDate: {},
weekKeys: {},
};
return {};
}
const shows = data
? await parseSheetToShowList(data, { apiKey: process.env.GA_API_KEY })
Expand Down
49 changes: 6 additions & 43 deletions scripts/google/showlistHelpers.ts
Original file line number Diff line number Diff line change
@@ -1,12 +1,5 @@
import {
addDays,
eachDayOfInterval,
eachWeekOfInterval,
format,
getISOWeek,
parse,
} from 'date-fns';
import { groupBy, head, keys, last } from 'ramda';
import { format } from 'date-fns';
import { groupBy } from 'ramda';

export enum Color {
Night = 'night',
Expand All @@ -24,38 +17,8 @@ export interface Show {
color?: Color | null;
}

export interface Showlist {
showsByDate: Record<string, Show[]>;
weekKeys: Record<string, string[]>;
}

export const showsToGroups = (shows: Show[]) => {
const showsByDate = groupBy(
(day: any) => format(new Date(day.start), 'y.M.dd'),
shows
);
const weekKeys = generateWeekObj(showsByDate);
return { showsByDate, weekKeys };
};

// Generate a nicely formatted object to use as keys.
const generateWeekObj = (showsByDate: Record<string, Show[]>) => {
const start = parse(head(keys(showsByDate)), 'y.M.dd', new Date());
const end = parse(last(keys(showsByDate)), 'y.M.dd', new Date());
const weeks = eachWeekOfInterval({ start, end }, { weekStartsOn: 1 });

const weekObj = weeks.reduce(
(acc: Record<string, string[]>, weekStart: Date) => {
const weekKey = getISOWeek(weekStart).toString();
const days = eachDayOfInterval({
start: weekStart,
end: addDays(new Date(weekStart), 6),
}).map((day: Date) => format(day, 'y.M.dd'));
acc[weekKey] = days;
return acc;
},
{}
);
// key is a date encoded as string, in the format YYYY.MM.DD
export type ShowsByDate = Record<string, Show[]>;

return weekObj;
};
export const showsToGroups = (shows: Show[]): ShowsByDate =>
groupBy((day: any) => format(new Date(day.start), 'y.M.dd'), shows);

0 comments on commit aa6e11d

Please sign in to comment.