Skip to content

Commit

Permalink
sync upcoming events component with API and hack work around for apos… (
Browse files Browse the repository at this point in the history
#46)

* sync upcoming events component with API and hack work around for apostrophes in JSON

* track hack work around
  • Loading branch information
thescientist13 authored Oct 20, 2022
1 parent a6945a1 commit c13032d
Show file tree
Hide file tree
Showing 4 changed files with 58 additions and 39 deletions.
27 changes: 16 additions & 11 deletions src/components/upcoming-events/mock-events.js
Original file line number Diff line number Diff line change
@@ -1,30 +1,35 @@
const SINGLE_EVENT = [{
title: 'Tuesdays Tunes Season 3 - Premier!',
timestamp: Date.now() + 300000,
title: 'Tuesday\'s Tunes Season 3 - Premier!',
startTime: Date.now() + 300000,
description: 'Lorem ipsum dolor sit amet, consectetur adipiscing elite.',
link: 'http://www.facebook.com/'
}];

// includes testing for multiple months, events list "overflow", and out of order events
const MULTIPLE_EVENTS = [{
title: 'Tuesdays Tunes Season 3 - Episode 1',
timestamp: SINGLE_EVENT[0].timestamp + (86400000 * 15),
title: 'Tuesday\'s Tunes Season 3 - Episode 1',
startTime: SINGLE_EVENT[0].startTime + (86400000 * 15),
description: 'Lorem ipsum dolor sit amet, consectetur adipiscing elite.',
link: 'http://www.facebook.com/'
}, {
...SINGLE_EVENT[0]
}, {
title: 'Tuesdays Tunes Season 3 - Episode 2',
timestamp: SINGLE_EVENT[0].timestamp + (86400000 * 30),
title: 'Tuesday\'s Tunes Season 3 - Episode 2',
startTime: SINGLE_EVENT[0].startTime + (86400000 * 30),
description: 'Lorem ipsum dolor sit amet, consectetur adipiscing elite.',
link: 'http://www.facebook.com/'
}, {
title: 'Tuesdays Tunes Season 3 - Teaser Trailer',
timestamp: SINGLE_EVENT[0].timestamp - (86400000 * 5),
title: 'Tuesday\'s Tunes Season 3 - Teaser Trailer',
startTime: SINGLE_EVENT[0].startTime - (86400000 * 5),
description: 'Lorem ipsum dolor sit amet, consectetur adipiscing elite.',
link: 'http://www.facebook.com/'
}, {
title: 'Tuesdays Tunes Season 3 - Episode 3',
timestamp: SINGLE_EVENT[0].timestamp + (86400000 * 45),
title: 'Tuesday\'s Tunes Season 3 - Episode 3',
startTime: SINGLE_EVENT[0].startTime + (86400000 * 45),
description: 'Lorem ipsum dolor sit amet, consectetur adipiscing elite.',
link: 'http://www.facebook.com/'
}];

const NO_EVENTS = [];

export { SINGLE_EVENT, MULTIPLE_EVENTS, NO_EVENTS };
export { SINGLE_EVENT, MULTIPLE_EVENTS, NO_EVENTS };
21 changes: 11 additions & 10 deletions src/components/upcoming-events/upcoming-events.js
Original file line number Diff line number Diff line change
Expand Up @@ -19,26 +19,26 @@ export default class UpcomingEvents extends HTMLElement {
const events = (JSON.parse(this.getAttribute('events')) || [])
.filter((event) => {
// filter out old events except ones that are also in the current month
const { timestamp } = event;
const { startTime } = event;
const now = new Date();

// set to be the beginning of the current month
now.setDate(1);
now.setFullYear(now.getFullYear());
now.setMonth(now.getMonth());

const isInCurrentMonth = timestamp >= now.getTime();
const isInCurrentMonth = startTime >= now.getTime();

return event.timestamp >= now.getTime() || isInCurrentMonth;
return startTime >= now.getTime() || isInCurrentMonth;
})
.sort((a, b) => a.timestamp < b.timestamp ? -1 : 1); // sort newest to latest
.sort((a, b) => a.startTime < b.startTime ? -1 : 1); // sort newest to latest
const noEvents = events.length === 0
? '<h2 class="text-center">No Upcoming Events</h2>'
: '';

// group events by month
events.forEach((event) => {
const time = new Date(event.timestamp);
const time = new Date(event.startTime);
const month = time.getMonth();
const monthKey = MONTH_INDEX_MAPPER[month];

Expand Down Expand Up @@ -66,11 +66,12 @@ export default class UpcomingEvents extends HTMLElement {
</h2>
${eventsByMonth[month].map((event) => {
const { link, timestamp, title } = event;
const time = new Date(timestamp);
const { link, startTime, title } = event;
const time = new Date(startTime);
const formattedTitle = title.replace(/"/g, '\''); // TODO https://github.com/AnalogStudiosRI/www.tuesdaystunes.tv/issues/47
const date = time.getDate();
const hour = time.getHours() - 12; // here we assume an 8pm (e.g. afternoon) start time
return `
<div>
<h3
Expand All @@ -79,7 +80,7 @@ export default class UpcomingEvents extends HTMLElement {
>
<a
href="${link}"
alt="${title}"
alt="${formattedTitle}"
>
<span
class="inline-block w-8 text-center"
Expand All @@ -90,7 +91,7 @@ export default class UpcomingEvents extends HTMLElement {
<span
style="color:var(--color-secondary);"
>
${title} @ ${hour}pm
${formattedTitle} @ ${hour}pm
</span>
</a>
</h3>
Expand Down
43 changes: 30 additions & 13 deletions src/components/upcoming-events/upcoming-events.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -54,17 +54,17 @@ describe('Components/Upcoming Events', () => {

it('should display the correct month heading', () => {
const headings = events.querySelectorAll('h2');
const time = new Date(SINGLE_EVENT[0].timestamp);
const time = new Date(SINGLE_EVENT[0].startTime);
const month = time.getMonth();
const monthLabel = MONTH_INDEX_MAPPER[month];

expect(headings[0].textContent).to.contain(monthLabel);
});

it('should display the correct date details', () => {
const { title, timestamp } = SINGLE_EVENT[0];
const { title, startTime } = SINGLE_EVENT[0];
const headings = events.querySelectorAll('h3');
const time = new Date(timestamp);
const time = new Date(startTime);
const date = time.getDate();
const hour = time.getHours() - 12;
const display = `${date}${title}@${hour}pm`.replace(/ /g, '');
Expand Down Expand Up @@ -101,35 +101,35 @@ describe('Components/Upcoming Events', () => {
it('should not display the no upcoming events text', () => {
const headings = events.querySelectorAll('h2');

expect(headings.length).to.equal(2);
expect(headings.length).to.greaterThanOrEqual(2); // sometimes events will spread over three months
expect(headings[0].textContent).to.not.equal('No Upcoming Events');
});

it('should display the correct month heading', () => {
const headings = events.querySelectorAll('h2');
const eventsByMonth = {};
const eventsByMonth = [];

MULTIPLE_EVENTS.forEach((event) => {
const time = new Date(event.timestamp);
ORDERED_EVENTS.forEach((event) => {
const time = new Date(event.startTime);
const month = time.getMonth();
const monthKey = MONTH_INDEX_MAPPER[month];

if (!eventsByMonth[monthKey]) {
eventsByMonth[monthKey] = true;
if (!eventsByMonth.includes(monthKey)) {
eventsByMonth.push(monthKey);
}
});

headings.forEach((heading, idx) => {
expect(heading.textContent).to.contain(Object.keys(eventsByMonth)[idx]);
expect(heading.textContent).to.contain(eventsByMonth[idx]);
});
});

it('should display the correct date details', () => {
const headings = events.querySelectorAll('h3');

headings.forEach((heading, idx) => {
const { title, timestamp } = ORDERED_EVENTS[idx];
const time = new Date(timestamp);
const { title, startTime } = ORDERED_EVENTS[idx];
const time = new Date(startTime);
const date = time.getDate();
const hour = time.getHours() - 12;
const display = `${date}${title}@${hour}pm`.replace(/ /g, '');
Expand Down Expand Up @@ -157,6 +157,23 @@ describe('Components/Upcoming Events', () => {
});
});

describe('No events attribute', () => {
before(async () => {
events = document.createElement('tt-upcoming-events');

document.body.appendChild(events);

await events.updateComplete;
});

it('should only display the no upcoming events text', () => {
const headings = events.querySelectorAll('h2');

expect(headings.length).to.equal(1);
expect(headings[0].textContent).to.equal('No Upcoming Events');
});
});

after(() => {
events.remove();
events = null;
Expand Down
6 changes: 1 addition & 5 deletions src/components/upcoming-events/upcoming-events.stories.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,11 +6,7 @@ export default {
title: 'Components/Upcoming Events'
};

// TODO mock data with an apostrophe will not work here, e.g. 'Tuesday\'s Tunes Season 3 - Premier!'
// If I use double quote everything stops at the first double quote, e.g. `[{`
// If I use single quote, it stops at the first single quote, e.g. `[{"title":"Tuesday`
// works fine when using `setAttribute` and the DOM 🤷
const Template = ({ events }) => `<tt-upcoming-events events='${JSON.stringify(events)}'></tt-upcoming-events>`;
const Template = ({ events }) => `<tt-upcoming-events events='${JSON.stringify(events).replace(/'/g, '\\"')}'></tt-upcoming-events>`;

export const Primary = Template.bind({});

Expand Down

0 comments on commit c13032d

Please sign in to comment.