diff --git a/apps/formbricks-com/.env.example b/apps/formbricks-com/.env.example index 4ce4f05a17..26b2ce211f 100644 --- a/apps/formbricks-com/.env.example +++ b/apps/formbricks-com/.env.example @@ -1,3 +1,6 @@ NEXT_PUBLIC_FORMBRICKS_COM_API_HOST=http://localhost:3000 NEXT_PUBLIC_FORMBRICKS_COM_ENVIRONMENT_ID= -NEXT_PUBLIC_FORMBRICKS_COM_DOCS_FEEDBACK_SURVEY_ID= \ No newline at end of file +NEXT_PUBLIC_FORMBRICKS_COM_DOCS_FEEDBACK_SURVEY_ID= + +# Strapi API Key +STRAPI_API_KEY= diff --git a/apps/formbricks-com/components/shared/LayoutMdx.tsx b/apps/formbricks-com/components/shared/LayoutMdx.tsx index dffad54af3..585f9d2107 100644 --- a/apps/formbricks-com/components/shared/LayoutMdx.tsx +++ b/apps/formbricks-com/components/shared/LayoutMdx.tsx @@ -1,8 +1,8 @@ +import { useEffect } from "react"; import Footer from "./Footer"; import Header from "./Header"; import MetaInformation from "./MetaInformation"; import { Prose } from "./Prose"; -import { useEffect } from "react"; const useExternalLinks = (selector: string) => { useEffect(() => { diff --git a/apps/formbricks-com/components/shared/MetaInformation.tsx b/apps/formbricks-com/components/shared/MetaInformation.tsx index 57ab4a8e16..39961f3c52 100644 --- a/apps/formbricks-com/components/shared/MetaInformation.tsx +++ b/apps/formbricks-com/components/shared/MetaInformation.tsx @@ -4,6 +4,7 @@ interface Props { title: string; description: string; publishedTime?: string; + updatedTime?: string; authors?: string[]; section?: string; tags?: string[]; @@ -13,6 +14,7 @@ export default function MetaInformation({ title, description, publishedTime, + updatedTime, authors, section, tags, @@ -31,9 +33,10 @@ export default function MetaInformation({ - - + + {publishedTime && } + {updatedTime && } {authors && } {section && } {tags && } diff --git a/apps/formbricks-com/next.config.mjs b/apps/formbricks-com/next.config.mjs index 60309722c6..339e699170 100644 --- a/apps/formbricks-com/next.config.mjs +++ b/apps/formbricks-com/next.config.mjs @@ -1,14 +1,23 @@ /** @type {import('next').NextConfig} */ +import rehypePrism from "@mapbox/rehype-prism"; import nextMDX from "@next/mdx"; import { withPlausibleProxy } from "next-plausible"; import remarkGfm from "remark-gfm"; -import rehypePrism from "@mapbox/rehype-prism"; const nextConfig = { reactStrictMode: true, pageExtensions: ["ts", "tsx", "js", "jsx", "md", "mdx"], transpilePackages: ["@formbricks/ui", "@formbricks/lib"], + images: { + remotePatterns: [ + { + protocol: "https", + hostname: "seo-strapi-aws-s3.s3.eu-central-1.amazonaws.com", + port: "", + }, + ], + }, async redirects() { return [ { diff --git a/apps/formbricks-com/package.json b/apps/formbricks-com/package.json index fc1d6087ad..4b3f02d7da 100644 --- a/apps/formbricks-com/package.json +++ b/apps/formbricks-com/package.json @@ -27,12 +27,15 @@ "lottie-web": "^5.12.2", "next": "13.4.12", "next-plausible": "^3.10.1", + "next-seo": "^6.1.0", "next-sitemap": "^4.1.8", + "node-fetch": "^3.3.2", "prism-react-renderer": "^2.0.6", "prismjs": "^1.29.0", "react": "18.2.0", "react-dom": "18.2.0", "react-icons": "^4.10.1", + "react-markdown": "^8.0.7", "react-responsive-embed": "^2.1.0", "remark-gfm": "^3.0.1", "sharp": "^0.32.4" diff --git a/apps/formbricks-com/pages/blog/best-open-source-survey-software-2023/index.mdx b/apps/formbricks-com/pages/blog/best-open-source-survey-software-2023/index.mdx index 79233124ae..fcb738a7c5 100644 --- a/apps/formbricks-com/pages/blog/best-open-source-survey-software-2023/index.mdx +++ b/apps/formbricks-com/pages/blog/best-open-source-survey-software-2023/index.mdx @@ -1,12 +1,12 @@ import Image from "next/image"; import LayoutMdx from "@/components/shared/LayoutMdx"; +import AuthorBox from "@/components/shared/AuthorBox"; import Formbricks from "./open-source-survey-software-free-2023-formbricks-typeform-alternative.png"; import Typebot from "./typebot-open-source-free-conversational-form-builder-survey-software-opensource.jpg"; import LimeSurvey from "./free-survey-tool-limesurvey-open-source-software-opensource.png"; import OpnForm from "./opnform-free-open-source-form-survey-tools-builder-2023-self-hostign.jpg"; import HeaderImage from "./2023-title-best-open-source-survey-software-tools-and-alternatives.png"; import SurveyJS from "./surveyjs-free-opensource-form-survey-tool-software-to-make-surveys-2023.png"; -import AuthorBox from "@/components/shared/AuthorBox"; export const meta = { title: "5 Open Source Survey and Form Tools maintained in 2023", diff --git a/apps/formbricks-com/pages/learn/[slug].tsx b/apps/formbricks-com/pages/learn/[slug].tsx new file mode 100644 index 0000000000..6462e0b78e --- /dev/null +++ b/apps/formbricks-com/pages/learn/[slug].tsx @@ -0,0 +1,141 @@ +import LayoutMdx from "@/components/shared/LayoutMdx"; +import { FAQPageJsonLd } from "next-seo"; +import Image from "next/image"; +import fetch from "node-fetch"; +import ReactMarkdown from "react-markdown"; + +type Article = { + id?: number; + attributes?: { + author?: string; + title?: string; + text?: string; + slug?: string; + createdAt?: string; + updatedAt?: string; + publishedAt?: string; + meta?: { + id?: number; + description?: string; + title?: string; + publisher?: string; + section?: string; + tags?: { + id?: number; + tag?: string; + }[]; + }; + faq?: { + id?: number; + question?: string; + answer?: string; + }[]; + }; +}; + +type ArticlePageProps = { + article?: Article; +}; + +interface ArticleResponse { + data: Article[]; + meta: { + pagination: { + page: number; + pageSize: number; + pageCount: number; + total: number; + }; + }; +} + +export async function getStaticPaths() { + const response = await fetch( + "https://strapi.formbricks.com/api/articles?populate[meta][populate]=*&filters[category][name][$eq]=learn", + { + headers: { + Authorization: `Bearer ${process.env.STRAPI_API_KEY}`, + }, + } + ); + if (!response.ok) { + throw new Error(`HTTP error! Status: ${response.status}`); + } + + const articles = (await response.json()) as ArticleResponse; + + const paths = articles.data.map((article) => ({ + params: { slug: article.attributes.slug }, + })); + + return { paths, fallback: true }; +} + +export async function getStaticProps({ params }) { + const res = await fetch( + `https://strapi.formbricks.com/api/articles?populate[meta][populate]=*&populate[faq][populate]=*&filters[slug][$eq]=${params.slug}`, + { + headers: { + Authorization: `Bearer ${process.env.STRAPI_API_KEY}`, + }, + } + ); + if (!res.ok) { + throw new Error("Something went wrong"); + } + const resData = (await res.json()) as ArticleResponse; + const article = resData.data[0]; + return { props: { article } }; +} + +export default function ArticlePage({ article = {} }: ArticlePageProps) { + if (!article || !article.attributes) return
{product.name} /
+{product.name} /
{ @@ -180,9 +180,11 @@ export default function SurveyMenuBar({ />+ This survey received responses. To keep the data consistent, make changes with caution. +