diff --git a/scripts/fetchMeetupData.js b/scripts/fetchMeetupData.js index f9781fc..4e3eeb0 100644 --- a/scripts/fetchMeetupData.js +++ b/scripts/fetchMeetupData.js @@ -1,12 +1,15 @@ import { writeFile } from "node:fs/promises"; +const MEETUP_URL = "https://www.meetup.com/ottawa-forwardjs-meetup"; +const MEETUP_ID = "28909672"; + async function writeJsonToFile(filename, jsonData) { const jsonString = JSON.stringify(jsonData, null, 2); await writeFile(filename, jsonString + "\n", "utf8"); } -async function fetchEvents(url) { +async function getNextDataJsonFromPage(url) { // fetch the page and get the HTML content const response = await fetch(url); const htmlContent = await response.text(); @@ -20,12 +23,27 @@ async function fetchEvents(url) { .replace('", ""); - // parse the data to JSON in the hackiest way possible - const parsedData = JSON.parse(JSON.parse(JSON.stringify(data))); + return data; +} +function getApolloState(parsedData) { // get the APOLLO_STATE from the parsed json const state = parsedData.props.pageProps.__APOLLO_STATE__; + return state; +} + +function doubleParseJson(data) { + // parse the data to JSON in the hackiest way possible + const parsedData = JSON.parse(JSON.parse(JSON.stringify(data))); + return parsedData; +} + +async function fetchMeetupEvents(url) { + const data = await getNextDataJsonFromPage(url); + const parsedData = doubleParseJson(data); + const state = getApolloState(parsedData); + // extract event data from the apollo state const events = []; for (const key of Object.keys(state)) { @@ -81,16 +99,32 @@ async function fetchEvents(url) { return events; } +async function fetchMeetupStats(url) { + const data = await getNextDataJsonFromPage(url); + const parsedData = doubleParseJson(data); + const state = getApolloState(parsedData); + + const { memberCounts, eventRatings } = state[`Group:${MEETUP_ID}`].stats; + + return { + memberCount: memberCounts.all, + organizerCount: memberCounts.leadership, + averageEventRating: eventRatings.average, + totalEventRatings: eventRatings.total, + }; +} + async function main() { try { - const upcoming = await fetchEvents( - "https://www.meetup.com/ottawa-forwardjs-meetup/events/?type=upcoming", + const meetupStats = await fetchMeetupStats(MEETUP_URL); + await writeJsonToFile("./src/data/meetupStats.json", meetupStats); + + const upcoming = await fetchMeetupEvents( + `${MEETUP_URL}/events/?type=upcoming`, ); await writeJsonToFile("./src/data/upcomingEvents.json", upcoming); - const past = await fetchEvents( - "https://www.meetup.com/ottawa-forwardjs-meetup/events/?type=past", - ); + const past = await fetchMeetupEvents(`${MEETUP_URL}/events/?type=past`); // write the last 5 past events to the JSON files await writeJsonToFile("./src/data/pastEvents.json", past.slice(0, 5)); } catch (error) { diff --git a/src/components/Navigation.astro b/src/components/Navigation.astro index 3e366d0..260eeb8 100644 --- a/src/components/Navigation.astro +++ b/src/components/Navigation.astro @@ -34,6 +34,7 @@ import logo from "../assets/forward.svg"; >
  • Job Board
  • +
  • What We're About
  • diff --git a/src/data/meetupStats.json b/src/data/meetupStats.json new file mode 100644 index 0000000..2d40589 --- /dev/null +++ b/src/data/meetupStats.json @@ -0,0 +1,6 @@ +{ + "memberCount": 2183, + "organizerCount": 8, + "averageEventRating": 4.78, + "totalEventRatings": 549 +} diff --git a/src/data/organizers.json b/src/data/organizers.json new file mode 100644 index 0000000..d9d63f4 --- /dev/null +++ b/src/data/organizers.json @@ -0,0 +1,67 @@ +[ + { + "firstName": "Brian", + "lastName": "Farias Tavares", + "joined": "Jun, 2018", + "role": "Co-organizer", + "imageUrl": "https://secure.meetupstatic.com/photos/member/2/9/3/b/highres_321310555.jpeg", + "altText": "Photo of Brian Farias Tavares" + }, + { + "firstName": "Eric", + "lastName": "Adamski", + "joined": "Jun, 2018", + "role": "Co-organizer", + "imageUrl": "https://secure.meetupstatic.com/photos/member/7/3/1/6/highres_257489462.jpeg", + "altText": "Photo of Eric Adamski" + }, + { + "firstName": "Renee", + "lastName": "Ghattas", + "joined": "Jun, 2018", + "role": "Co-organizer", + "imageUrl": "https://secure.meetupstatic.com/photos/member/4/a/6/e/highres_316399054.jpeg", + "altText": "Photo of Renne Ghattas" + }, + { + "firstName": "Simon", + "lastName": "MacDonald", + "joined": "Jun, 2018", + "role": "Co-organizer", + "imageUrl": "https://secure.meetupstatic.com/photos/member/2/b/7/e/highres_314171134.jpeg", + "altText": "Photo of Simon MacDonald" + }, + + { + "firstName": "Rey", + "lastName": "Riel", + "joined": "Jun, 2018", + "role": "Co-organizer", + "imageUrl": "https://secure.meetupstatic.com/photos/member/5/8/5/highres_259921413.jpeg", + "altText": "Photo of Rey Riel" + }, + { + "firstName": "Matt", + "lastName": "Dupont", + "joined": "Feb, 2023", + "role": "Co-organizer", + "imageUrl": "https://secure.meetupstatic.com/photos/member/6/7/4/d/highres_277526445.jpeg", + "altText": "Photo of Matt Dupont" + }, + { + "firstName": "Ameya", + "lastName": "Charnalia", + "joined": "Feb, 2023", + "role": "Co-organizer", + "imageUrl": "https://secure.meetupstatic.com/photos/member/5/b/f/f/highres_308843551.jpeg", + "altText": "Photo of Ameya Charnalia" + }, + { + "firstName": "Matt", + "lastName": "Millard", + "joined": "Sep, 2023", + "role": "Co-organizer", + "imageUrl": "https://secure.meetupstatic.com/photos/member/9/d/0/3/highres_317140195.jpeg", + "altText": "Photo of Matt Millard" + } +] diff --git a/src/pages/what-were-about.astro b/src/pages/what-were-about.astro new file mode 100644 index 0000000..cd52c00 --- /dev/null +++ b/src/pages/what-were-about.astro @@ -0,0 +1,174 @@ +--- +import organizers from "../data/organizers.json"; +import { memberCount } from "../data/meetupStats.json"; +import Layout from "../layouts/Layout.astro"; +--- + + +
    +
    +

    What We're About

    +

    + ForwardJS Ottawa (formerly React Ottawa) is a non-profit tech meetup + group dedicated to web development technologies and community. +

    +

    + Founded in 2018, we now have + {memberCount.toLocaleString()} members + and host monthly events that bring developers together to learn, share, and + connect. +

    +

    We host two types of events:

    +
      +
    • Traditional meetups with guest speakers and tech talks.
    • +
    • Casual socials focused on community building.
    • +
    + +

    Join Us

    +

    + Whether you're just getting started or you're deep into your dev career, + we'd love to have you join us.
    + + Become a member and get notified about upcoming events! +

    +
    + +
    +

    Meet Our Organizers

    + +
    + { + organizers.map((organizer) => { + return ( +
    +
    + + {organizer.altText} + +
    +

    + {organizer.firstName} {organizer.lastName} +

    +

    {organizer.role}

    +

    Joined {organizer.joined}

    +
    +
    +
    + ); + }) + } +
    +
    +
    + + +