Search code examples
javascriptjsonasync-awaitsession-storage

Save fetched JSON data to sessionStorage


I just figured out how to write an async/await function to fetch data from an API, and it's working, but it's hitting the API like crazy. So now I'm trying to save the fetched data to sessionStorage and only fetch from the API if the data isn't in the sessionStorage.

Here's my code:

const fetchMeetingData = async () => {
    console.log('api hit')
    try {
        const response = await fetch(https://sheet.best...)
        const data = await response.json()
        validate(data) // Clean data to remove null key values
        return data
    } catch (e) {
        console.log('Fetch error with getMeetingData()')
    }
}

const filterMeetings = async (filters) => {
    meetings = await fetchMeetingData()
    meetings.forEach((meeting) => {
        meeting.time2 = moment(meeting.time, ["h:mm A"]).format("HHmm")
    })
    let today = moment().format("dddd").toString()
    let hour = moment().format('HHmm').toString()
    let filteredMeetings = meetings.filter(function (matches) {
        if (document.querySelector('#select-day').selectedIndex === 0 && filters.searchText === '') {
            return matches.day === today &&
                moment(matches.time, ["h:mm A"]).format("HHmm") > hour
        } else {
            return true
        }
    })

Here's what I've tried:

const fetchMeetingData = async () => {
    console.log('api hit')
    try {
        const response = await fetch(https://sheet.best...)
        const data = await response.json()
        validate(data) // Clean data to remove null key values
        sessionStorage.setItem('meetingData', JSON.stringify(data)) // added this line
        return data
    } catch (e) {
        console.log('Whoa! Fetch error with getMeetingData()')
    }
}

I'm not really sure where to go from here, or if this is even the correct approach. My noob instinct was to do something like this, which didn't work.

savedMeetingData = sessionStorage.getItem('meetingData')

const getSavedMeetingData = async () => {
    if (savedMeetingData) {
        meetings = savedMeetingData
        return meetings
    } else {
        fetchMeetingData()
        meetings = await data
        return meetings
    }

const filterMeetings = async (filters) => {
    meetings = await getSavedMeetingData() // replaces call to fetchMeetingData
    meetings.forEach((meeting) => {
        meeting.time2 = moment(meeting.time, ["h:mm A"]).format("HHmm")
    })

I'm not sure if that's exactly the code I was trying but it's close. The problem was the API was still getting hit, even though the data was stored successfully to sessionStorage.

I'd really appreciate some help and/or suggestions on how to clarify this question.

SOLUTION: Based on answer from @Christian

// StackOverflow Q/A
async function getMeetingData() {
    const preLoadedData = sessionStorage.getItem('meetingData')
    if(!preLoadedData) {
        try {
            const response = await fetch('https://sheet.best...')
            const data = await response.json()
            validate(data)
            sessionStorage.setItem('meetingData', JSON.stringify(data))
            console.log('api hit')
            return data
        } catch (e) {
            console.log('Whoa! Fetch error with getMeetingData()')
        }
    } else {
        console.log('no api hit!!!')
        return JSON.parse(preLoadedData)
    }
}
async function getSavedMeetingData() {
    const meetings = await getMeetingData()
    return meetings
}
const filterMeetings = async (filters) => {
    meetings = await getSavedMeetingData()
    meetings.forEach((meeting) => {
        meeting.time2 = moment(meeting.time, ["h:mm A"]).format("HHmm")
    })

Solution

  • If you could be more explicit on what exactly did not work it would be great :) (did not save data in sessionStorage?, could not retrieve it?, etc...). Anyway, maybe you could try something like this and see if it helps:

    async function getSavedMeetingData() {
      const meetingData = await getMeetingData();
    }
    
    async function getMeetingData() {
      const preloadedData = sessionStorage.getItem('meetingData');
    
      if (!preloadedData) {
        try {
          const response = await fetch('https://myapiurl.com/');
          const data = validate(response.json());
          sessionStorage.setItem('meetingData', JSON.stringify(data));
          return data;
        } catch (e) {
          console.log('Whoa! Fetch error with getMeetingData()');
        }
      } else {
        return JSON.parse(preloadedData);
      }
    }
    

    One more reminder (just in case), keep in mind you are saving this to sessionStorage, so if you close the tab do not expect to have the information saved, in that case you should use localStorage.