Skip to content

Commit

Permalink
Add server side rendering to commodities list
Browse files Browse the repository at this point in the history
  • Loading branch information
iaincollins committed Sep 14, 2024
1 parent 30d2bfb commit ba7e07f
Show file tree
Hide file tree
Showing 8 changed files with 93 additions and 61 deletions.
16 changes: 10 additions & 6 deletions lib/commodities.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,20 +4,24 @@ import { API_BASE_URL } from 'lib/consts'

const allCommodities = [...allRegularCommodities, ...allRareCommodities]

async function getCommodities () {
const res = await fetch(`${API_BASE_URL}/v1/commodities`)
const commoditiesOnServer = await res.json()
async function getCommodities (rawCommoditiesData) {
// Use rawCommoditiesData if provided, else fetch data from server
let latestCommoditiesData = rawCommoditiesData
if (!latestCommoditiesData) {
const res = await fetch(`${API_BASE_URL}/v1/commodities`)
latestCommoditiesData = await res.json()
}

// Blend canonical list of commodities with commodity info from server, if
// the server has info about that commodity. The list on the server is likely
// be a subset as not all commodities actively traded all the time.
return allCommodities
.map(commodityInfo => {
const commodityFromServer = (commoditiesOnServer.find(el => commodityInfo.symbol.toLowerCase() === el.commodityName.toLowerCase()))
const commodity = (commodityFromServer) ? { ...commodityInfo, ...commodityFromServer } : commodityInfo
const latestCommodityData = (latestCommoditiesData.find(el => commodityInfo.symbol.toLowerCase() === el.commodityName.toLowerCase()))
const commodity = (latestCommodityData) ? { ...commodityInfo, ...latestCommodityData } : commodityInfo

// Normalize properties to make the objects easy to work with in components
commodity.key = commodity.commodityId
commodity.key = commodity?.commodityId ?? null
commodity.avgProfit = commodity.avgSellPrice - commodity.avgBuyPrice
commodity.avgProfitMargin = Math.floor((commodity.avgProfit / commodity.avgBuyPrice) * 100)
commodity.maxProfit = commodity.maxSellPrice - commodity.minBuyPrice
Expand Down
8 changes: 8 additions & 0 deletions next.config.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,12 @@
module.exports = {
async rewrites () {
return [
{
source: '/',
destination: '/commodities'
}
]
},
async redirects () {
return [
{
Expand Down
2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
{
"name": "ardent-www",
"version": "0.47.4",
"version": "0.48.0",
"description": "Ardent Industry",
"main": "index.js",
"scripts": {
Expand Down
14 changes: 7 additions & 7 deletions pages/_app.js
Original file line number Diff line number Diff line change
Expand Up @@ -34,9 +34,9 @@ export default class MyApp extends App {
}

function Sphere (props) {
const ref1 = useRef(),
ref2 = useRef(),
ref3 = useRef()
const ref1 = useRef()
const ref2 = useRef()
const ref3 = useRef()
useFrame((state, delta) => (ref1.current.rotation.y -= (delta / 32)))
useFrame((state, delta) => (ref2.current.rotation.x -= (delta / 16)))
useFrame((state, delta) => (ref3.current.rotation.z += (delta / 64)))
Expand All @@ -47,7 +47,7 @@ function Sphere (props) {
ref={ref1}
position={[3, 0, 0]}
scale={2}
rotation={[-10,0,0]}
rotation={[-10, 0, 0]}
>
<mesh>
<sphereGeometry args={[2, 64, 64]} />
Expand All @@ -63,7 +63,7 @@ function Sphere (props) {
ref={ref2}
position={[3, 0, 0]}
scale={2}
rotation={[-10,0,0]}
rotation={[-10, 0, 0]}
>
<mesh>
<sphereGeometry args={[2.8, 32, 32]} />
Expand All @@ -75,14 +75,14 @@ function Sphere (props) {
ref={ref3}
position={[3, 0, 0]}
scale={2}
rotation={[-10,0,0]}
rotation={[-10, 0, 0]}
>
<mesh>
<sphereGeometry args={[3, 16, 16]} />
<meshStandardMaterial color='#ccc' wireframe />
</mesh>
</group>
</>
</>
)
}

Expand Down
15 changes: 13 additions & 2 deletions pages/_document.js
Original file line number Diff line number Diff line change
Expand Up @@ -18,10 +18,21 @@ class MyDocument extends Document {
<Head>
<meta name='theme-color' content='#000' />
<style dangerouslySetInnerHTML={{
__html: 'html { background: black; }'
__html: 'html{background:#000;}'
}}
/>
<script dangerouslySetInnerHTML={{ __html: onContextMenu }} />
<noscript>
<style dangerouslySetInnerHTML={{
__html: `
table.data-table--animated > tbody > tr:not(.rc-table-expanded-row),
.data-table--animated > .rc-table-container > .rc-table-content > table > tbody > tr:not(.rc-table-expanded-row) {
opacity: 1 !important;
}
`.trim()
}}
/>
</noscript>
</Head>
<body>
<div dangerouslySetInnerHTML={{
Expand All @@ -40,7 +51,7 @@ class MyDocument extends Document {
if (isSafari) document.documentElement.setAttribute("data-browser", "safari")
if (isFirefox) document.documentElement.setAttribute("data-browser", "firefox")
</script>
`
`.trim()
}}
/>
<Main />
Expand Down
2 changes: 1 addition & 1 deletion pages/about.js
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ export default () => {
}, [])

return (
<Layout
<Layout
title='About Ardent Industry for Elite Dangerous'
description='Ardent Industry is companion software for the game Elite Dangerous.'
>
Expand Down
43 changes: 26 additions & 17 deletions pages/commodities.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,17 @@ import Layout from 'components/layout'
import { getCommodities } from 'lib/commodities'
import animateTableEffect from 'lib/animate-table-effect'

export default () => {
export async function getServerSideProps () {
const rawCommoditiesData = (await import('../../ardent-data/cache/commodities.json')).commodities
const commodities = await getCommodities(rawCommoditiesData)
const categories = [...new Set(commodities.map((c) => c.category).sort())]
return { props: { commodities, categories } }
}

export default function Page (props) {
const router = useRouter()
const [commodities, setCommodities] = useState()
const [categories, setCategories] = useState()
const [commodities, setCommodities] = useState(props.commodities)
const [categories, setCategories] = useState(props.categories)

const onRowClick = (record, index, event) => {
router.push(`/commodity/${record.commodityName}`)
Expand All @@ -19,10 +26,12 @@ export default () => {

useEffect(() => {
(async () => {
const commodities = await getCommodities()
const categories = [...new Set(commodities.map((c) => c.category).sort())]
setCommodities(commodities)
setCategories(categories)
if (!commodities || !categories) {
const commodities = await getCommodities()
const categories = [...new Set(commodities.map((c) => c.category).sort())]
setCommodities(commodities)
setCategories(categories)
}
})()
}, [])

Expand Down Expand Up @@ -52,7 +61,7 @@ export default () => {
render: (v, r) =>
<>
<i className='icon icarus-terminal-cargo' />
{v}{r.market_id && <>{' '}<span className='muted'>(Rare)</span></>}<br />
{v}{r.market_id && <>{' '}<span className='muted'>(Rare)</span></>}<br />
<small>
{r.category}
</small>
Expand All @@ -63,9 +72,8 @@ export default () => {
<td><span className='data-table__label'>Avg Import CR/T</span>
{!r.market_id
? <>{r.avgSellPrice > 0 ? <>{r.avgSellPrice.toLocaleString()} CR</> : '-'}</>
: <span className='muted'>-</span>
}
</td>
: <span className='muted'>-</span>}
</td>
<td><span className='data-table__label'>Avg Profit CR/T</span>{r.avgProfit > 0 ? <>{r.avgProfit.toLocaleString()} CR</> : '-'}</td>
</tr>
<tr>
Expand All @@ -83,12 +91,13 @@ export default () => {
key: 'avgSellPrice',
align: 'right',
className: 'is-hidden-mobile',
render: (v, r) => (v > 0) ? <>
{!r.market_id
? <>{v.toLocaleString()} CR</>
: <span className='muted'>-</span>
}
</> : '-'
render: (v, r) => (v > 0)
? <>
{!r.market_id
? <>{v.toLocaleString()} CR</>
: <span className='muted'>-</span>}
</>
: '-'
},
{
title: 'Avg export CR/T',
Expand Down
54 changes: 27 additions & 27 deletions pages/commodity/[commodity-name]/index.js
Original file line number Diff line number Diff line change
Expand Up @@ -104,12 +104,12 @@ export default () => {
}, [])

return (
<Layout
loading={commodity === undefined}
loadingText='Loading trade data'
title={commodity ? `${commodity.name} in Elite Dangerous` : null}
description={commodity ? `Where to buy and sell ${commodity.name} in Elite Dangerous` : null}
>
<Layout
loading={commodity === undefined}
loadingText='Loading trade data'
title={commodity ? `${commodity.name} in Elite Dangerous` : null}
description={commodity ? `Where to buy and sell ${commodity.name} in Elite Dangerous` : null}
>
<Head>
<link rel='canonical' href={`https://ardent-industry.com/system/${commodity?.symbol}/${tabs[tabIndex]}`} />
</Head>
Expand Down Expand Up @@ -146,7 +146,8 @@ export default () => {
? <>
{((commodity.avgSellPrice + 16000) / 2).toLocaleString()} CR/T
{' '}
<small>({commodity.minSellPrice.toLocaleString()} - {(commodity.minSellPrice + 16000).toLocaleString()} CR)</small>
{typeof commodity.avgSellPrice === 'number' &&
<small>({commodity.minSellPrice.toLocaleString()} - {(commodity.minSellPrice + 16000).toLocaleString()} CR)</small>}
</>
: <>
{typeof commodity.avgSellPrice === 'number'
Expand Down Expand Up @@ -187,7 +188,7 @@ export default () => {
{commodity.avgProfit.toLocaleString()} CR/T
{' '}
<small>({commodity.avgProfitMargin}% margin)</small>
</>}
</>}
</span>
</td>
</tr>}
Expand Down Expand Up @@ -223,27 +224,26 @@ export default () => {
</span>
</td>
</tr>
</>
}
{/* <p className='clear muted' style={{ padding: '0 0 1rem .25rem' }}>
</>}
{/* <p className='clear muted' style={{ padding: '0 0 1rem .25rem' }}>
Galactic prices and total supply/demand updated daily
</p> */}
{commodity.rare &&
<tr>
<th>
<i className='icon icarus-terminal-info' style={{ marginRight: '.25rem' }} />
RARE GOODS
</th>
<td>
<p style={{margin: 0, textTransform: 'none'}}>
Rare goods are only available in limited quantities from exclusive locations but can be sold almost anywhere.
</p>
<p style={{margin: '.5rem 0 0 0', textTransform: 'none'}}>
They increase in value the further they are traded from the source, reaching maximum value when traded
around 150-200 ly away.
</p>
</td>
</tr>}
{commodity.rare &&
<tr>
<th>
<i className='icon icarus-terminal-info' style={{ marginRight: '.25rem' }} />
RARE GOODS
</th>
<td>
<p style={{ margin: 0, textTransform: 'none' }}>
Rare goods are only available in limited quantities from exclusive locations but can be sold almost anywhere.
</p>
<p style={{ margin: '.5rem 0 0 0', textTransform: 'none' }}>
They increase in value the further they are traded from the source, reaching maximum value when traded
around 150-200 ly away.
</p>
</td>
</tr>}
</tbody>
</table>
<Tabs
Expand Down

0 comments on commit ba7e07f

Please sign in to comment.