Skip to content

Commit

Permalink
Merge pull request #85 from medyo/develop
Browse files Browse the repository at this point in the history
Version 1.12.1
  • Loading branch information
medyo authored Feb 7, 2022
2 parents b3c03a8 + 88febd6 commit 6530ebb
Show file tree
Hide file tree
Showing 10 changed files with 140 additions and 100 deletions.
6 changes: 6 additions & 0 deletions src/cards/ReposCard.js
Original file line number Diff line number Diff line change
Expand Up @@ -88,6 +88,11 @@ function ReposCard({ analyticsTag, label, icon, withAds }) {
}, [selectedDateRange])

const fetchRepos = async () => {

if (!selectedLanguage) {
return []
}

if (!selectedLanguage?.githubValues) {
throw Error(`Github Trending does not support ${selectedLanguage.label}.`)
}
Expand Down Expand Up @@ -123,6 +128,7 @@ function ReposCard({ analyticsTag, label, icon, withAds }) {

setCacheCardData({ ...cacheCardData, [cacheKey]: data })
return data

}

function HeaderTitle() {
Expand Down
30 changes: 15 additions & 15 deletions src/components/ListComponent.js
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
import React, { useState, useEffect } from "react";
import BeatLoader from "react-spinners/BeatLoader";
import CarbonAd from './CarbonAd'
import { trackException } from '../utils/Analytics'

function ListComponent({ fetchData, refresh, renderItem, withAds }) {
const [items, setItems] = useState([])
Expand All @@ -14,11 +15,10 @@ function ListComponent({ fetchData, refresh, renderItem, withAds }) {
try {
const data = await fetchData()
setItems(data)
}
catch (e) {
} catch (e) {
setError(e)
}
finally {
trackException(e, true)
} finally {
setLoading(false)
}
}
Expand All @@ -27,16 +27,16 @@ function ListComponent({ fetchData, refresh, renderItem, withAds }) {
}, [refresh])

if (error) {
return (<p className="errorMsg">{error.message}</p>)
return <p className="errorMsg">{error.message}</p>
}

const renderItems = () => {
if (!items || items.length == 0 ) {
<p className="errorMsg">Could not find any content using the selected languages!</p>
if (!items) {
return
}
return items.map((item, index) => {
let content = [renderItem(item, index)]
if(withAds && index == 0) {
if (withAds && index == 0) {
content.unshift(<CarbonAd key={'carbonAd0'} />)
}
return content
Expand All @@ -45,13 +45,13 @@ function ListComponent({ fetchData, refresh, renderItem, withAds }) {

return (
<>
{
loading ?
<div className="cardLoading">
<BeatLoader color={"#A9B2BD"} loading={loading} size={15} className="loading" />
</div> : renderItems()
}

{loading ? (
<div className="cardLoading">
<BeatLoader color={'#A9B2BD'} loading={loading} size={15} className="loading" />
</div>
) : (
renderItems()
)}
</>
)
}
Expand Down
32 changes: 32 additions & 0 deletions src/configuration/AppErrorBoundary.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
import React, { useContext } from 'react'
import { ErrorBoundary } from 'react-error-boundary'
import { trackException } from '../utils/Analytics'
import { AiFillBug } from 'react-icons/ai'
import { WiRefresh } from 'react-icons/wi'
import { APP } from '../Constants'
import '../pages/Page.css'

export default function AppErrorBoundary({ children }) {
function ErrorFallback({ error, resetErrorBoundary }) {
return (
<div className="Page appError">
<AiFillBug size={64} />
<p>Sorry there was a problem loading this page.</p>
<p>{error}</p>
<button onClick={resetErrorBoundary}>
<WiRefresh size={32} className={'buttonIcon'} /> Try again
</button>
</div>
)
}

const errorHandler = (error, info) => {
trackException(error, true)
}

return (
<ErrorBoundary FallbackComponent={ErrorFallback} onError={errorHandler}>
{children}
</ErrorBoundary>
)
}
21 changes: 21 additions & 0 deletions src/configuration/AppLoadingHOC.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
import React, { useState } from 'react'
import BeatLoader from 'react-spinners/BeatLoader'

export const AppLoadingHOC = (WrappedComponent) => {
function HOC(props) {
const [isLoading, setIsLoading] = useState(true)
const setLoadingState = (isComponentLoading) => setIsLoading(isComponentLoading)

return (
<>
{isLoading && (
<div className="appLoading">
<BeatLoader color={'#A9B2BD'} loading={true} size={15} />
</div>
)}
<WrappedComponent {...props} setLoading={setLoadingState} isLoading={isLoading} />
</>
)
}
return HOC
}
37 changes: 7 additions & 30 deletions src/configuration/AppWrapper.js
Original file line number Diff line number Diff line change
@@ -1,31 +1,14 @@
import React, { useReducer, useContext } from 'react'
import { LS_PREFERENCES_KEY } from '../Constants'
import AppStorage from '../services/localStorage'
import { PreferencesProvider } from '../preferences/PreferencesContext'
import { getOSMode } from '../services/os'
import AppReducer from '../preferences/AppReducer'
import { PreferencesProvider } from '../preferences/PreferencesContext'
import ConfigurationContext from './ConfigurationContext'
import { ErrorBoundary } from 'react-error-boundary'
import { trackException } from '../utils/Analytics'
import { AiFillBug } from 'react-icons/ai'
import { WiRefresh } from 'react-icons/wi'
import { APP, LS_PREFERENCES_KEY } from '../Constants'
import AppStorage from '../services/localStorage'
import '../pages/Page.css'

function ErrorFallback({ error, resetErrorBoundary }) {
return (
<div className="Page appError">
<AiFillBug size={64} />
<p>Sorry there was a problem loading this page.</p>
<p>Please try again or contact the developer at {APP.contactEmail}</p>
<button onClick={resetErrorBoundary}>
<WiRefresh size={32} className={'buttonIcon'} /> Try again
</button>
</div>
)
}

export default function AppWrapper({ children }) {
const configuration = useContext(ConfigurationContext)

const [state, dispatcher] = useReducer(
AppReducer,
{
Expand Down Expand Up @@ -62,15 +45,9 @@ export default function AppWrapper({ children }) {
}
)

const errorHandler = (error, info) => {
trackException(error, true)
}

return (
<ErrorBoundary FallbackComponent={ErrorFallback} onError={errorHandler}>
<PreferencesProvider value={{ ...state, dispatcher: dispatcher }}>
{children}
</PreferencesProvider>
</ErrorBoundary>
<PreferencesProvider value={{ ...state, dispatcher: dispatcher }}>
{children}
</PreferencesProvider>
)
}
53 changes: 34 additions & 19 deletions src/configuration/ConfigurationWrapper.js
Original file line number Diff line number Diff line change
@@ -1,24 +1,39 @@
import useRemoteConfiguration from './useRemoteConfiguration';
import { ConfigurationProvider } from './ConfigurationContext';
import { LOCAL_CONFIGURATION } from '../Constants';
import BeatLoader from "react-spinners/BeatLoader";
import AppWrapper from './AppWrapper'
import React, { useEffect, useState } from 'react'
import remoteConfigurationApi from '../services/remoteConfiguration'
import { ConfigurationProvider } from './ConfigurationContext'
import { AppLoadingHOC } from './AppLoadingHOC'
import useAsyncError from '../hooks/useAsyncError'

export default function ConfigurationWrapper({ children }) {
const [configuration, loadingConfiguration, errorConfiguration] = useRemoteConfiguration()
if (loadingConfiguration) {
return (
<div className="appLoading">
<BeatLoader color={'#A9B2BD'} loading={true} size={15} />
</div>
)
}
export const ConfigurationWrapper = (props) => {
const { setLoading, isLoading } = props
const [configurationData, setConfigurationData] = useState(null)
const throwError = useAsyncError()

const getConfiguration = () => (errorConfiguration ? LOCAL_CONFIGURATION : configuration)
useEffect(() => {
setLoading(true)
const setup = async () => {
// try {
const data = await remoteConfigurationApi.getRemoteConfiguration()
if (!data) {
throwError(
'Could not fetch configuration data, Make sure you are connected to the internet'
)
} else {
setConfigurationData(data)
}
setLoading(false)
}

setup()
}, [])

return (
<ConfigurationProvider value={getConfiguration()}>
<AppWrapper>{children}</AppWrapper>
</ConfigurationProvider>
<>
{configurationData && (
<ConfigurationProvider value={configurationData}>{props.children}</ConfigurationProvider>
)}
</>
)
}
}

export default AppLoadingHOC(ConfigurationWrapper)
31 changes: 0 additions & 31 deletions src/configuration/useRemoteConfiguration.js

This file was deleted.

14 changes: 14 additions & 0 deletions src/hooks/useAsyncError.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
import React, { useCallback, useState } from 'react'

const useAsyncError = () => {
const [_, setError] = useState()
return useCallback(
(e) => {
setError(() => {
throw e
})
},
[setError]
)
}
export default useAsyncError
14 changes: 10 additions & 4 deletions src/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,19 @@ import ReactDOM from 'react-dom';
import 'normalize.css';
import './index.css';
import App from './App';
import AppWrapper from './configuration/AppWrapper'
import AppErrorBoundary from './configuration/AppErrorBoundary'
import ConfigurationWrapper from './configuration/ConfigurationWrapper'

ReactDOM.render(
<React.StrictMode>
<ConfigurationWrapper>
<App />
</ConfigurationWrapper>
<AppErrorBoundary>
<ConfigurationWrapper>
<AppWrapper>
<App />
</AppWrapper>
</ConfigurationWrapper>
</AppErrorBoundary>
</React.StrictMode>,
document.getElementById('root')
);
)
2 changes: 1 addition & 1 deletion src/services/cachedRequest.js
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ const cachedRequest = async (url) => {
}
} catch (error) {
if (!error.response || error.response.status !== 304) {
throw error
return null //throw error
}
if (!cachedResponse) {
throw 'Network Failed'
Expand Down

0 comments on commit 6530ebb

Please sign in to comment.