From d93815ae735843281bcc9cbec8a8d3424a358d83 Mon Sep 17 00:00:00 2001 From: Christopher Gurnee Date: Thu, 3 Mar 2022 09:10:35 -0500 Subject: [PATCH] Improve error handling and move it to API layer --- src/api/pushshift/index.js | 19 ++++++++++++------- src/api/reddit/index.js | 21 ++++++++++++++++----- src/pages/thread/index.js | 24 ++++-------------------- 3 files changed, 32 insertions(+), 32 deletions(-) diff --git a/src/api/pushshift/index.js b/src/api/pushshift/index.js index da0a193..2b9fe05 100644 --- a/src/api/pushshift/index.js +++ b/src/api/pushshift/index.js @@ -4,6 +4,14 @@ export const chunkSize = 100; const postURL = 'https://api.pushshift.io/reddit/submission/search/?ids=' const commentURL = `https://api.pushshift.io/reddit/comment/search/?size=${chunkSize}&sort=asc&fields=author,body,created_utc,id,link_id,parent_id,retrieved_on,retrieved_utc,score,subreddit&q=*&link_id=` +const errorHandler = (msg, origError, from) => { + console.error(from + ': ' + origError) + const error = new Error(msg) + if (origError.name == 'TypeError') // Usually indicates that Pushshift is down + error.helpUrl = '/about#psdown' + throw error +} + const sleep = ms => new Promise(slept => setTimeout(slept, ms)) @@ -62,8 +70,7 @@ export const getPost = async threadID => { try { return (await fetchJson(`${postURL}${threadID}`)).data[0] } catch (error) { - console.error('pushshift.getPost: ' + error) - throw new Error('Could not get removed post') + errorHandler('Could not get removed post', error, 'pushshift.getPost') } } @@ -75,13 +82,11 @@ export const getComments = async (allComments, threadID, maxComments, after) => while (true) { await pushshiftTokenBucket.waitForToken() try { - comments = (await fetchJson(`${commentURL}${threadID}&after=${after}`)).data + comments = (await fetchJson(`${commentURL}${threadID}${after ? `&after=${after}` : ''}`)).data break } catch (error) { - if (delay >= 8000) { // after ~16s of consecutive failures - console.error('pushshift.getComments: ' + error) - throw new Error('Could not get removed comments') - } + if (delay >= 8000) // after ~16s of consecutive failures + errorHandler('Could not get removed comments', error, 'pushshift.getComments') // rethrows delay = delay * 2 || 125 console.log('pushshift.getComments delay: ' + delay) pushshiftTokenBucket.setNextAvail(delay) diff --git a/src/api/reddit/index.js b/src/api/reddit/index.js index af595ef..9c84a67 100644 --- a/src/api/reddit/index.js +++ b/src/api/reddit/index.js @@ -3,11 +3,22 @@ import { fetchJson, chunk } from '../../utils' const baseURL = 'https://api.reddit.com' const requestSettings = {headers: {"Accept-Language": "en"}} -const errorHandler = (error, from) => { - console.error(from + ': ' + error) - const e = new Error('Could not connect to Reddit') - e.origError = error - throw e +const errorHandler = (origError, from) => { + console.error(from + ': ' + origError) + const error = new Error('Could not connect to Reddit') + if (origError.name == 'TypeError') { // The exception when blocked by Tracking Protection + // https://stackoverflow.com/a/9851769 + const isFirefox = typeof InstallTrigger !== 'undefined' + if (isFirefox) + error.helpUrl = '/about#firefox' + else { + const isChrome = !!window.chrome && (!!window.chrome.webstore || !!window.chrome.runtime) + const isEdgeChromium = isChrome && (navigator.userAgent.indexOf("Edg") != -1) + if (isEdgeChromium) + error.helpUrl = '/about#edge' + } + } + throw error } // Return the post itself diff --git a/src/pages/thread/index.js b/src/pages/thread/index.js index 1222638..687f895 100644 --- a/src/pages/thread/index.js +++ b/src/pages/thread/index.js @@ -59,6 +59,7 @@ class Thread extends React.Component { } this.setState({ post: removedPost }) }) + .catch(e => this.props.global.setError(e, e.helpUrl)) } }) .catch(error => { @@ -70,7 +71,7 @@ class Thread extends React.Component { this.setState({ post: { ...removedPost, removed: true } }) }) .catch(error => { - this.props.global.setError(error) + this.props.global.setError(error, error.helpUrl) // Create a dummy post so that comments will still be displayed this.setState({ post: { subreddit, id: threadID } }) }) @@ -168,26 +169,9 @@ class Thread extends React.Component { reloadingComments: false }) }) - .catch(e => { - if (e.origError.name == 'TypeError') { // The exception when blocked by Tracking Protection - // https://stackoverflow.com/a/9851769 - const isFirefox = typeof InstallTrigger !== 'undefined' - if (isFirefox) { - this.props.global.setError(e, '/about#firefox') - return - } else { - const isChrome = !!window.chrome && (!!window.chrome.webstore || !!window.chrome.runtime) - const isEdgeChromium = isChrome && (navigator.userAgent.indexOf("Edg") != -1) - if (isEdgeChromium) { - this.props.global.setError(e, '/about#edge') - return - } - } - } - throw e - }) + .catch(e => this.props.global.setError(e, e.helpUrl)) }) - .catch(this.props.global.setError) + .catch(e => this.props.global.setError(e, e.helpUrl)) } render () {