Skip to content

Commit

Permalink
add series navigator
Browse files Browse the repository at this point in the history
 - move blog content into _content director, refactor how mdsvex page components are loaded
 - add dynamic import plugin
 - add series navigator component
 - add [slug].svelte, series/[slug].svelte, series/[slug].json pages
 - uncomment series component on homepage
 - tests
 - random small bug fixes
  • Loading branch information
ryanfiller committed Mar 7, 2021
1 parent e939c36 commit 9022382
Show file tree
Hide file tree
Showing 26 changed files with 269 additions and 36 deletions.
45 changes: 45 additions & 0 deletions cypress/integration/components/blog/series-navigator.spec.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
describe('<SeriesNavigator /> component', () => {
context('when it should not exist', () => {
beforeEach(() => {
cy.visit('/blog/fighting-with-git-lfs')
})

it('does not render', () => {
cy.get('.series-navigator__title').should('not.exist')
cy.get('.series-navigator__buttons').should('not.exist')
})
})

context('when it should exist', () => {
beforeEach(() => {
cy.visit('/blog/series')
// navigate to the first post
cy.get('.post-preview-list').find('a').eq(0).click()
cy.injectAxe()
})

it('renders correctly', () => {
cy.get('.series-navigator__title').contains('This is post 1 of')
cy.get('.series-navigator__buttons').within(() => {
cy.get('.series-navigator__previous').should('not.exist')
cy.get('.series-navigator__next').should('exist')
})
// cy.checkA11y('.series-navigator__title')
// cy.checkA11y('.series-navigator__buttons')
})

it('navigates forward and backwards', () => {
cy.get('.series-navigator__buttons').within(() => {
cy.get('.series-navigator__next').click()
})
cy.reload() // why???
cy.get('.series-navigator__title').contains('This is post 2 of')
cy.get('.series-navigator__buttons').within(() => {
cy.get('.series-navigator__previous').should('exist')
cy.get('.series-navigator__previous').click()
})
cy.reload() // why???
cy.get('.series-navigator__title').contains('This is post 1 of')
})
})
})
2 changes: 1 addition & 1 deletion cypress/integration/routes/blog-series-json.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@ describe('/blog/series.json route', () => {
if (index > 0) {
date = new Date(date).getTime()
const previousDate = new Date(dates[index - 1]).getTime()
expect(date < previousDate).to.be.true
expect(date > previousDate).to.be.true
}
})
})
Expand Down
2 changes: 1 addition & 1 deletion cypress/integration/routes/generate-image.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,7 @@ describe('/generate-image route', () => {

const params = objectToParams({
title: 'test title',
excerpt: 'short expcert',
excerpt: 'short excerpt',
categories: ['one fish', 'two fish'],
tags: ['red fish', 'blue fish'],
imageSrc: '/images/site-assets/_placeholder.jpg',
Expand Down
2 changes: 2 additions & 0 deletions cypress/integration/routes/rss.spec.js
Original file line number Diff line number Diff line change
Expand Up @@ -38,7 +38,9 @@ describe('/blog/rss.xml', () => {
]
cy.request('/blog/rss.xml')
.then(({body}) => {
console.log('body', body)
const items = body.match(/<item>(.|\n)*?<\/item>/g)
console.log('items', items)
expect(items).to.have.length.of.at.most(12)
items.map(item => {
itemTags.map(tag => {
Expand Down
Binary file not shown.
Binary file not shown.
34 changes: 34 additions & 0 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

1 change: 1 addition & 0 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,7 @@
"devDependencies": {
"@cypress/snapshot": "^2.1.7",
"@rollup/plugin-commonjs": "^12.0.0",
"@rollup/plugin-dynamic-import-vars": "^1.1.1",
"@rollup/plugin-node-resolve": "^8.0.0",
"@rollup/plugin-replace": "^2.2.0",
"color-contrast-table-svelte": "^3.0.8",
Expand Down
7 changes: 7 additions & 0 deletions rollup.config.js
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ import { terser } from 'rollup-plugin-terser'
import config from 'sapper/config/rollup.js'
import pkg from './package.json'
import { mdsvex } from 'mdsvex'
import dynamicImportVars from '@rollup/plugin-dynamic-import-vars'
import svelteSVG from 'rollup-plugin-svelte-svg'
import { globalStyle, scss } from 'svelte-preprocess'
import copy from 'rollup-plugin-copy'
Expand Down Expand Up @@ -43,6 +44,10 @@ const envVars = {
exclude: 'src/routes/**/*.md'
}

const dynamicImportVarsOptions = {
include: `src/routes/**/*.svelte`
}

const preprocess = [
mdsvex({
extension: '.md',
Expand Down Expand Up @@ -104,6 +109,7 @@ export default {
dedupe: ['svelte']
}),
commonjs(),
dynamicImportVars(dynamicImportVarsOptions),
svelteSVG({ dev }),
copy({
targets: [
Expand Down Expand Up @@ -139,6 +145,7 @@ export default {
dedupe: ['svelte']
}),
commonjs(),
dynamicImportVars(dynamicImportVarsOptions),
svelteSVG({ generate: 'ssr', dev }),
copy({
targets: [
Expand Down
4 changes: 2 additions & 2 deletions snapshots.js

Large diffs are not rendered by default.

86 changes: 86 additions & 0 deletions src/components/blog/series-navigator.svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,86 @@
<script>
import { getContext } from 'svelte'
const series = getContext('series')
let postIndex
let previous
let next
$: if (series) {
postIndex = series.posts.findIndex(post => post.title === $$props.title)
if (series.posts[postIndex - 1]) {
previous = series.posts[postIndex - 1]
}
if (series.posts[postIndex + 1]) {
next = series.posts[postIndex + 1]
}
}
</script>

<style global type='text/scss'>
.series-navigator {
&__title {
color: var(--colorWhite);
background: var(--colorHighlight);
text-align: center;
padding: var(--padding);
a {
color: inherit;
&:not(:hover) {
text-decoration: none;
}
}
}
&__buttons {
background: var(--colorHighlight);
display: flex;
}
&__previous,
&__next {
flex-wrap: wrap;
width: 50%;
&:before {
font-size: .8em;
margin-bottom: calc(.5 * var(--padding));
display: block;
}
}
&__previous {
text-align: right;
margin-right: auto;
&:before {
content: '« previous';
}
}
&__next {
text-align: left;
margin-left: auto;
&:before {
content: 'next »';
}
}
}
</style>

{#if series}
<aside class='series-navigator__title'>
This is post {postIndex + 1} of {series.posts.length} in the <a href={series.slug}>{series.title}</a> series.
</aside>

<slot />

<aside class='series-navigator__buttons'>
{#if previous}
<a href={previous.slug} class='series-navigator__previous button'>
{previous.title}
</a>
{/if}
{#if next}
<a href={next.slug} class='series-navigator__next button'>
{next.title}
</a>
{/if}
</aside>

{:else}
<slot />
{/if}
2 changes: 1 addition & 1 deletion src/components/layout/seo.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -60,7 +60,7 @@
imageCredit: banner.attribution ? banner.attribution : '',
url: pageUrl.replace('https://www.', '')
})
local && console.log('imageFunctionUrl', `${host}/.netlify/functions/generate-image?${imageParams}`)
// local && console.log('imageFunctionUrl', `${host}/.netlify/functions/generate-image?${imageParams}`)
socialImageUrl = `https://res.cloudinary.com/${process.env.CLOUDINARY_CLOUD}/image/upload/social-images/${slugify(title)}.png`
}
</script>
Expand Down
3 changes: 2 additions & 1 deletion src/helpers/get-pages.js
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,8 @@ const getPosts = ({

return ({
...frontmatter,
slug: `${directory}/${post}`,
// TODO remove _content from this helper method all together
slug: `/${directory.replace('/_content', '')}/${post}`,
html: html
})
})
Expand Down
9 changes: 6 additions & 3 deletions src/layouts/blog.svelte
Original file line number Diff line number Diff line change
@@ -1,10 +1,13 @@
<script>
import Page from './page.svelte'
import Markdown from '../components/layout/markdown.svelte'
import SeriesNavigator from '../components/blog/series-navigator.svelte'
</script>

<Page {...$$props} >
<Markdown>
<slot />
</Markdown>
<SeriesNavigator {...$$props}>
<Markdown>
<slot />
</Markdown>
</SeriesNavigator>
</Page>
5 changes: 4 additions & 1 deletion src/layouts/page.svelte
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,10 @@
#content {
grid-area: content;
width: 100%;
max-height: 100%;
min-height: 100%;
display: flex;
flex-direction: column;
justify-content: space-between;
}
#site-footer {
Expand Down
32 changes: 32 additions & 0 deletions src/routes/blog/[slug].svelte
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
<script context='module'>
export async function preload(page) {
const { slug } = page.params
const component = await import(`./_content/${slug}/index.md`)
const series = await this.fetch(`/blog/series.json`)
.then(response => response.json())
.then(allSeries => allSeries.find(series => {
const postSlugs = series.posts.map(series => series.slug.replace('/blog/', ''))
if (postSlugs.includes(slug)) {
return series
}
}))
return {
page: component.default,
metadata: component.metadata,
series: series
}
}
</script>

<script>
export let page
export let series
import { setContext } from 'svelte'
setContext('series', series)
</script>

<svelte:component this={page} />
2 changes: 1 addition & 1 deletion src/routes/blog/index.json.js
Original file line number Diff line number Diff line change
Expand Up @@ -5,5 +5,5 @@ export function get(_req, res) {
'Content-Type': 'application/json'
})

res.end(JSON.stringify(getPages({directory: 'blog'})))
res.end(JSON.stringify(getPages({directory: 'blog/_content'})))
}
2 changes: 1 addition & 1 deletion src/routes/blog/rss.xml.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ export async function get(req, res) {
const category = req.query.category || null

const posts = getPages({
directory: 'blog',
directory: 'blog/_content',
returnBody: true,
category: category,
slice: [0, 12]
Expand Down
16 changes: 16 additions & 0 deletions src/routes/blog/series/[slug].json.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,16 @@

import fetch from 'node-fetch'

export async function get(req, res) {
res.writeHead(200, {
'Content-Type': 'application/json'
})

const slug = req.path.match(/(.*)\.json/)[1]

const series = await fetch('http://localhost:3000/blog/series.json')
.then(response => response.json())
.then(series => series.find(series => series.slug === slug))

res.end(JSON.stringify(series))
}
8 changes: 2 additions & 6 deletions src/routes/blog/series/[slug].svelte
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
<script context='module'>
export function preload({ params, query }) {
return this.fetch(`/blog/series.json`)
return this.fetch(`/blog/series/${params.slug}.json`)
.then(response => response.json())
.then(series => {
return { series }
Expand All @@ -10,10 +10,6 @@

<script>
export let series
import { stores } from '@sapper/app'
const { page } = stores()
series = series.filter(series => series.slug = $page.params.slug)[0]
const preview = {...series, title: ''}
import Page from '../../../layouts/page.svelte'
Expand All @@ -23,4 +19,4 @@

<Page {...series}>
<SeriesPreview {...preview} />
</Page>
</Page>

0 comments on commit 9022382

Please sign in to comment.