Skip to content
New issue

Have a question about this project? # for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “#”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? # to your account

✨ Landing: Add storyblok CMS #2938

Merged
merged 6 commits into from
Aug 2, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
3 changes: 2 additions & 1 deletion .github/workflows/landing-deploy.yml
Original file line number Diff line number Diff line change
Expand Up @@ -21,6 +21,7 @@ jobs:
run: pnpm -F shepherd.js build
- uses: superfly/flyctl-actions/setup-flyctl@master
- run: |
flyctl deploy --config landing/fly.toml --dockerfile landing/Dockerfile --build-secret PUBLIC_SHEPHERD_PUBLIC_KEY=${{ secrets.PUBLIC_SHEPHERD_PUBLIC_KEY }}
flyctl deploy --config landing/fly.toml --dockerfile landing/Dockerfile --build-secret STORYBLOK_TOKEN=${{ secrets.STORYBLOK_TOKEN }}
env:
FLY_API_TOKEN: ${{ secrets.FLY_API_TOKEN }}
STORYBLOK_TOKEN: ${{ secrets.STORYBLOK_TOKEN }}
4 changes: 2 additions & 2 deletions landing/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -35,8 +35,8 @@ COPY --link ./landing ./landing
RUN pnpm install --frozen-lockfile --prod=false

# Build application
RUN --mount=type=secret,id=PUBLIC_SHEPHERD_PUBLIC_KEY \
SHEPHERD_PUBLIC_KEY="$(cat /run/secrets/PUBLIC_SHEPHERD_PUBLIC_KEY)" \
RUN --mount=type=secret,id=STORYBLOK_TOKEN \
STORYBLOK_TOKEN="$(cat /run/secrets/STORYBLOK_TOKEN)" \
pnpm -F landing run build

# Remove development dependencies
Expand Down
22 changes: 18 additions & 4 deletions landing/astro.config.mjs
Original file line number Diff line number Diff line change
@@ -1,14 +1,28 @@
import { defineConfig } from 'astro/config';
import mdx from '@astrojs/mdx';
import sitemap from '@astrojs/sitemap';
import storyblok from '@storyblok/astro';
import tailwind from '@astrojs/tailwind';
import { loadEnv } from 'vite';

const { STORYBLOK_TOKEN } = loadEnv(process.env.NODE_ENV, process.cwd(), '');

// https://astro.build/config
export default defineConfig({
site: 'https://blog.shepherdpro.com',
integrations: [mdx(), sitemap(), tailwind()],
redirects: {
'/blog': '/'
}
integrations: [
mdx(),
sitemap(),
storyblok({
accessToken: STORYBLOK_TOKEN,
apiOptions: {
region: 'us'
},
components: {
'all-articles': 'storyblok/AllArticles',
article: 'storyblok/Article'
}
}),
tailwind()
],
});
7 changes: 5 additions & 2 deletions landing/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -16,13 +16,16 @@
"@astrojs/rss": "^4.0.7",
"@astrojs/sitemap": "^3.1.6",
"@astrojs/tailwind": "^5.1.0",
"astro": "^4.12.0",
"@storyblok/astro": "^5.0.0",
"@storyblok/js": "^3.0.8",
"astro": "^4.13.0",
"shepherd.js": "workspace:*",
"tailwindcss": "^3.4.3",
"typescript": "^5.5.3"
},
"devDependencies": {
"@tailwindcss/typography": "^0.5.13",
"sharp": "^0.33.4"
"sharp": "^0.33.4",
"vite": "^5.3.2"
}
}
26 changes: 26 additions & 0 deletions landing/src/components/ArticleCard.astro
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
---
const { article } = Astro.props;
---

<article class="column feature bg-gray-100 rounded">
<img
class="object-cover object-center w-full lg:h-48 md:h-36 rounded"
src={`${article.image.filename}/m/360x240`}
alt={article.image.alt}
/>
<div class="p-4">
<h1 class="text-2xl font-semibold lg:text-3xl">
{article.title}
</h1>
<p class="leading-relaxed text-gray-700 line-clamp-2 my-4">
{article.teaser}
</p>
<a
href={`/blog/${article.slug}`}
class="font-semibold text-blue-600 hover:underline"
title="read more"
>
Read More »
</a>
</div>
</article>
2 changes: 1 addition & 1 deletion landing/src/components/BaseHead.astro
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@ interface Props {

const canonicalURL = new URL(Astro.url.pathname, Astro.url.origin);

const { title, description, image = '/blog-placeholder-1.jpg' } = Astro.props;
const { title, description } = Astro.props;
---

<!-- Global Metadata -->
Expand Down
9 changes: 1 addition & 8 deletions landing/src/layouts/MainPage.astro
Original file line number Diff line number Diff line change
@@ -1,16 +1,9 @@
---
import { Code } from 'astro:components';
import Base from './Base.astro';
import Header from '../components/Header.astro';
import Footer from '../components/Footer.astro';
import GithubButton from '../components/GithubButton.astro';
import { SITE_TITLE } from '../consts';

const shepherdIncludeCode = `
<link rel="stylesheet" href="shepherd.js/dist/css/shepherd.css"/>
<script type="module" src="shepherd.js/dist/shepherd.mjs"></script>

`;
---

<Base>
Expand Down Expand Up @@ -109,4 +102,4 @@ const shepherdIncludeCode = `
</div>
</main>
<Footer />
</Base>
</Base>
44 changes: 44 additions & 0 deletions landing/src/pages/[...slug].astro
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
---
import { useStoryblokApi } from '@storyblok/astro';
import StoryblokComponent from '@storyblok/astro/StoryblokComponent.astro';
import BlogPost from '@layouts/BlogPost.astro';

export async function getStaticPaths() {
const storyblokApi = useStoryblokApi();

const links = await storyblokApi.getAll('cdn/links', {
version: 'published'
});

return links
.filter((link) => !link.is_folder)
.map((link) => {
return {
params: {
slug: link.slug === 'home' ? undefined : link.slug
}
};
});
}

const { slug } = Astro.params;

const storyblokApi = useStoryblokApi();
const { data } = await storyblokApi.get(
`cdn/stories/${slug === undefined ? 'home' : slug}`,
{
version: 'published',
resolve_relations: ['all-articles.articles']
}
);

const story = data.story;
---

<BlogPost {...story}>
<div class="section flex flex-wrap justify-center">
<div class="max-w-4xl w-full">
<StoryblokComponent blok={story.content} />
</div>
</div>
</BlogPost>
2 changes: 0 additions & 2 deletions landing/src/pages/demo.astro
Original file line number Diff line number Diff line change
Expand Up @@ -83,8 +83,6 @@ const shepherdIncludeCode = `
</MainPage>

<script>
'use strict';

import Shepherd from 'shepherd.js';

(function () {
Expand Down
27 changes: 22 additions & 5 deletions landing/src/pages/index.astro
Original file line number Diff line number Diff line change
@@ -1,27 +1,44 @@
---
import { useStoryblokApi } from '@storyblok/astro';
import { getCollection } from 'astro:content';
import MainPage from '@layouts/MainPage.astro';

import Base from '@layouts/Base.astro';
import Header from '@components/Header.astro';
import Footer from '@components/Footer.astro';
import { SITE_TITLE } from '../consts';
import AllArticles from '@storyblok/AllArticles.astro';
import FormattedDate from '@components/FormattedDate.astro';

export async function getStaticPaths() {
const storyblokApi = useStoryblokApi();

const links = await storyblokApi.getAll('cdn/links', {
version: 'published'
});

return links
.filter((link) => !link.is_folder)
.map((link) => {
return {
params: {
slug: link.slug === 'home' ? undefined : link.slug
}
};
});
}

const posts = (await getCollection('blog')).sort(
(a, b) => b.data.pubDate.valueOf() - a.data.pubDate.valueOf()
);
---

<MainPage>
<section class="my-10 text-2xl w-full" slot="content">
<AllArticles />
<ul class="list-square text-left">
{
posts.map((post) => (
<li class="grid grid-cols-[1fr] md:grid-cols-[1fr_auto] mb-3 md:gap-2 items-start">
<div class="before:float-left before:leading-7 before:text-red-300 before:text-sm before:mr-2 before:content-['>>']">
<a
href={`/blog/${post.slug}`}
href={`/old-blog/${post.slug}`}
class="unset hover:text-navy-light"
>
<h4 class="font-bold font-title">{post.data.title}</h4>
Expand Down
53 changes: 53 additions & 0 deletions landing/src/storyblok/AllArticles.astro
Original file line number Diff line number Diff line change
@@ -0,0 +1,53 @@
---
import { storyblokEditable, useStoryblokApi } from '@storyblok/astro';
import FormattedDate from '@components/FormattedDate.astro';

type ArticleContent = {
slug: String;
title: String;
};

export type Article = {
content: ArticleContent;
created_at: Date;
slug: String;
};

const { blok } = Astro.props;

const storyblokApi = useStoryblokApi();
const { data } = await storyblokApi.get(`cdn/stories`, {
version: 'draft', // or 'published'
starts_with: 'blog/',
is_startpage: false
});

const articles = data.stories;
---

<ul class="list-square text-left" {...storyblokEditable(blok)}>
{
articles?.length &&
articles.map((article: Article) => {
article.content.slug = article.slug;
const created = new Date(article.created_at);
return (
<li class="grid grid-cols-[1fr] md:grid-cols-[1fr_auto] mb-3 md:gap-2 items-start">
<div class="before:float-left before:leading-7 before:text-red-300 before:text-sm before:mr-2 before:content-['>>']">
<a
href={`/blog/${article.slug}`}
class="unset hover:text-navy-light"
>
<h4 class="font-bold font-title">{article.content.title}</h4>
</a>
</div>
<div class="text-text-muted text-md italic">
<time datetime={created.toISOString()}>
<FormattedDate date={created} />
</time>
</div>
</li>
);
})
}
</ul>
28 changes: 28 additions & 0 deletions landing/src/storyblok/Article.astro
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
---
import { storyblokEditable, renderRichText } from '@storyblok/astro';

const { blok } = Astro.props;
const renderedRichText = renderRichText(blok.content);
---

<div class="container mx-auto mb-12" {...storyblokEditable(blok)}>
<h1 class="font-heading m-auto max-w-3xl my-8 text-5xl" itemprop="headline">
{blok.title}
</h1>
<figure>
<img
class="w-full h-[360px] lg:h-[450px] object-cover"
alt={blok.image.alt}
src={`${blok.image.filename}/m/1600x0`}
/>

<figcaption class="italic mb-12 text-gray-700">
{blok.image.title}
</figcaption>
</figure>

<div
class="prose max-w-none m-auto prose-headings:font-heading prose-headings:text-navy prose-p:font-body prose-p:text-gray-600 md:prose-lg lg:prose-xl"
set:html={renderedRichText}
/>
</div>
3 changes: 2 additions & 1 deletion landing/tsconfig.json
Original file line number Diff line number Diff line change
Expand Up @@ -4,7 +4,8 @@
"baseUrl": ".",
"paths": {
"@components/*": ["src/components/*"],
"@layouts/*": ["src/layouts/*"]
"@layouts/*": ["src/layouts/*"],
"@storyblok/*": ["src/storyblok/*"]
},
"strictNullChecks": true,
"verbatimModuleSyntax": true
Expand Down
6 changes: 3 additions & 3 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -13,8 +13,8 @@
"Chuck Carpenter <chuck@shipshape.io>"
],
"scripts": {
"prepare": "pnpm build",
"build": "pnpm -F shepherd.js build && pnpm -F '!shepherd.js' build",
"prepare": "pnpm -F shepherd.js build",
"build": "pnpm -F shepherd.js build && pnpm -F '!shepherd.js' -F !landing -F !shepherd-docs build",
"cypress:install": "pnpm -F 'cypress-tests' cypress:install",
"dev": "pnpm watch",
"docs": "node_modules/.bin/jsdoc -c .jsdoc.js --verbose",
Expand Down Expand Up @@ -49,7 +49,7 @@
"svelte": "^4.2.12",
"typescript": "^5.4.5"
},
"packageManager": "pnpm@8.15.4",
"packageManager": "pnpm@9.2.0",
"engines": {
"node": "18.* || >= 20"
}
Expand Down
Loading