Navigation Menu

Skip to content
This repository has been archived by the owner on Jun 13, 2022. It is now read-only.

Commit

Permalink
feat(docs): support sitemap generation and improve SEO
Browse files Browse the repository at this point in the history
  • Loading branch information
juliomrqz committed May 10, 2019
1 parent 29bfe4d commit c31c107
Show file tree
Hide file tree
Showing 42 changed files with 363 additions and 10 deletions.
5 changes: 4 additions & 1 deletion packages/docs/package.json
Expand Up @@ -42,6 +42,9 @@
"consola": "^2.6.1",
"fs-extra": "^7.0.1",
"markdown-it-block-image": "0.0.3",
"markdown-it-imsize": "^2.0.1"
"markdown-it-imsize": "^2.0.1",
"vuepress-plugin-reading-time": "^0.1.1",
"vuepress-plugin-seo": "^0.1.2",
"vuepress-plugin-sitemap": "^2.1.2"
}
}
63 changes: 57 additions & 6 deletions packages/docs/src/.vuepress/config.js
@@ -1,9 +1,30 @@
const axios = require('axios')
const webpack = require('webpack')

const { path, postcss } = require('@statusfy/common')

const { postcss, path } = require('@statusfy/common')
const partners = require('./partners.json')
const pkg = require('../../package.json')

const baseUrl = 'https://docs.statusfy.co'
const author = {
en: {
name: 'Bazzite',
twitter: 'BazziteTech'
},
es: {
name: 'Bazzite',
twitter: 'BazziteEs'
}
}

const getLang = $page => $page._computed.$lang.split('-')[0]
const getGitLastUpdatedTimeStamp = (filePath) => {
try {
return parseInt(spawn.sync('git', ['log', '-1', '--format=%ct', filePath]).stdout.toString('utf-8')) * 1000
} catch (e) {
return new Date()
}
}

module.exports = {
title: 'Statusfy Documentation',
Expand Down Expand Up @@ -46,6 +67,8 @@ module.exports = {
}
},
themeConfig: {
version: pkg.version,
domain: baseUrl,
repo: 'bazzite/statusfy',
docsRepo: 'bazzite/statusfy',
docsDir: 'packages/docs/src',
Expand All @@ -57,6 +80,7 @@ module.exports = {
} : null,
locales: {
'/': {
lang: 'en-US',
selectText: 'Languages',
label: 'English',
editLinkText: 'Help us improve this page!',
Expand Down Expand Up @@ -89,6 +113,7 @@ module.exports = {
}
},
'/es/': {
lang: 'es-US',
selectText: 'Idiomas',
label: 'Español',
editLinkText: '¡Ayúdanos a mejorar esta página!',
Expand Down Expand Up @@ -134,10 +159,12 @@ module.exports = {
}
},
chainWebpack (config) {
const themePath = path.resolve(__dirname, "../../../../", "node_modules/@vuepress/theme-default")

config.resolve.alias.set('@theme', themePath)
config.resolve.alias.set('@', path.resolve(themePath, "components"))
config.resolve.alias.set('@assets', path.resolve(__dirname, 'public/assets'))
config.resolve.alias.set('@public', path.resolve(__dirname, 'public'))
},
extendPageData($page) {
const timestamp = getGitLastUpdatedTimeStamp($page._filePath)
$page.lastUpdated = timestamp
},
plugins: [
['@vuepress/back-to-top', true],
Expand All @@ -164,6 +191,30 @@ module.exports = {
before: '<pre class="statusfy-container"><code>',
after: '</code></pre>',
}],
['seo', {
type: () => 'article',
author: $page => author[getLang($page)],
modifiedAt: $page => $page.frontmatter.lastUpdated,
customMeta: (add, context) => {
const { $page, modifiedAt } = context
const lang = getLang($page)

add('twitter:site', author[lang].twitter)
add('article:author', author[lang].name)
add('article:publisher', 'https://www.facebook.com/bazzite/')
add('article:modified_time', modifiedAt)

add('og:updated_time', modifiedAt)

add('fb:profile_id', '168475873515802')
},
}],
['sitemap', {
hostname: baseUrl,
changefreq: 'weekly'
}],
'vuepress-plugin-reading-time',
[require('./plugins/extra-seo')]
]
}

Expand Down
40 changes: 40 additions & 0 deletions packages/docs/src/.vuepress/plugins/extra-seo/ExtraSeo.vue
@@ -0,0 +1,40 @@
<template></template>

<script>
export default {
created() {
if (typeof this.$ssrContext !== "undefined") {
const { domain } = this.$site.themeConfig
const pagePath = this.$page.path.replace(/\.html$/, "")
const url = path => `${domain}${path}`
const lang = this.$lang.split('-')[0]
// canonical
this.$ssrContext.userHeadTags += `<link rel="canonical" href="${url(pagePath)}"/>`;
// alternate
let enPath;
let esPath;
if (pagePath.startsWith('/es/')) {
enPath = pagePath.substring(3)
esPath = pagePath
} else {
enPath = pagePath
esPath = `/es${pagePath}`
}
this.$ssrContext.userHeadTags += `<link rel="alternate" href="${url(enPath)}" hreflang="en-US"/>`;
this.$ssrContext.userHeadTags += `<link rel="alternate" href="${url(esPath)}" hreflang="es-US"/>`;
// logo
const logo = domain + require(`@assets/img/social-${lang}.png`)
this.$ssrContext.userHeadTags += `<meta name="twitter:image" content="${logo}">`;
this.$ssrContext.userHeadTags += `<meta property="og:image" content="${logo}">`;
this.$ssrContext.userHeadTags += `<meta property="og:image:width" content="2136">`;
this.$ssrContext.userHeadTags += `<meta property="og:image:height" content="1116">`;
}
}
};
</script>
@@ -0,0 +1,5 @@
import ExtraSeo from './ExtraSeo.vue'

export default ({ Vue, options }) => {
Vue.component('ExtraSeo', ExtraSeo)
}
8 changes: 8 additions & 0 deletions packages/docs/src/.vuepress/plugins/extra-seo/index.js
@@ -0,0 +1,8 @@
const { path } = require('@vuepress/shared-utils')

module.exports = options => ({
enhanceAppFiles () {
return [path.resolve(__dirname, 'enhanceAppFile.js')]
},
globalUIComponents: ['ExtraSeo']
})
2 changes: 2 additions & 0 deletions packages/docs/src/.vuepress/public/_redirects
@@ -0,0 +1,2 @@
# redirect html pages
/*.html /:splat/ 301
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
52 changes: 52 additions & 0 deletions packages/docs/src/.vuepress/theme/components/Page.vue
@@ -0,0 +1,52 @@
<template>
<div itemscope itemtype="http://schema.org/Article">
<meta itemprop="dateCreated" :content="$page.frontmatter.date">
<meta itemprop="datePublished" :content="$page.frontmatter.date">
<meta itemprop="dateModified" :content="$page.lastUpdated">
<meta itemprop="headline" :content="$page.title">
<meta itemprop="description" :content="$page.frontmatter.description">
<meta itemprop="inLanguage" :content="language">
<meta itemprop="mainEntityOfPage" :content="$site.themeConfig.domain + $page.path">
<meta itemprop="image" :content="require(`@assets/img/social-${language}.png`)">
<meta itemprop="wordCount" :content="$page.readingTime.words">
<meta itemprop="timeRequired" :content="`PT${Math.ceil($page.readingTime.minutes)}M`">
<meta itemprop="license" content="https://github.com/bazzite/statusfy/blob/develop/LICENSE">
<meta itemprop="version" :content="$site.themeConfig.version">
<div itemscope itemprop="author" itemtype="http://schema.org/Organization">
<meta itemprop="legalName" content="Bazzite, LLC">
<meta itemprop="name" content="Bazzite">
<meta itemprop="url" content="https://www.bazzite.com">
</div>
<div itemscope itemprop="publisher" itemtype="http://schema.org/Organization">
<meta itemprop="name" content="Statusfy">
<meta itemprop="url" content="https://statusfy.co">
<div itemscope itemscope itemprop="logo" itemtype="http://schema.org/ImageObject">
<meta itemprop="url" :content="require('@public/logo.png')">
<meta itemprop="width" content="512px">
<meta itemprop="height" content="512px">
</div>
</div>

<ParentPage :sidebarItems="sidebarItems" itemprop="articleBody" />
</div>
</template>

<script>
import ParentPage from '@parent-theme/components/Page.vue'
export default {
components: {
ParentPage
},
props: ['sidebarItems'],
mounted() {
console.log(this.$page)
console.log(this.$site)
},
computed: {
language() {
return this.$lang.split('-')[0];
}
}
}
</script>
1 change: 1 addition & 0 deletions packages/docs/src/README.md
@@ -1,4 +1,5 @@
---
date: 2018-10-12T17:28:04Z
home: true
heroImage: /hero.bvdrsr4sre5.svg
actionText: Get Started →
Expand Down
3 changes: 3 additions & 0 deletions packages/docs/src/config/README.md
@@ -1,4 +1,7 @@
---
title: Config Reference
description: Config Reference of Statusfy.
date: 2018-10-12T17:28:04Z
sidebar: auto
sidebarDepth: 2
---
Expand Down
3 changes: 3 additions & 0 deletions packages/docs/src/contributing/README.md
@@ -1,4 +1,7 @@
---
title: Contribution Guide
description: Statusfy is one of the Bazzite's Open Source Projects that is under very active development. We hope this document makes the process for contributing clear and answers some questions that you may have.
date: 2018-10-12T17:28:04Z
sidebar: auto
sidebarDepth: 3
---
Expand Down
1 change: 1 addition & 0 deletions packages/docs/src/es/README.md
@@ -1,4 +1,5 @@
---
date: 2018-10-12T17:28:04Z
home: true
heroImage: /hero.bvdrsr4sre5.svg
actionText: Empezemos →
Expand Down
3 changes: 3 additions & 0 deletions packages/docs/src/es/config/README.md
@@ -1,4 +1,7 @@
---
title: Referencia de Configuración
description: Referencia de Configuración de Statusfy.
date: 2018-10-12T17:28:04Z
sidebar: auto
sidebarDepth: 2
---
Expand Down
3 changes: 3 additions & 0 deletions packages/docs/src/es/contributing/README.md
@@ -1,4 +1,7 @@
---
title: Guía de Contribución
description: Statusfy es uno de los proyectos de código abierto de Bazzite que está en activo desarrollo. Esperamos que este documento haga que el proceso de contribución sea claro y que responda algunas preguntas que puedas tener.
date: 2018-10-12T17:28:04Z
sidebar: auto
sidebarDepth: 3
---
Expand Down
6 changes: 6 additions & 0 deletions packages/docs/src/es/guide/README.md
@@ -1,3 +1,9 @@
---
title: Introducción
description: Statusfy es un Sistema de Página de Estado, fácil de usar y completamente de código abierto. Puedes crear fácilmente un Sistema rápido, ya sea Stático o Renderizado por Servidor e implementarlo fácilmente en una variedad de servicios de alojamiento.
date: 2018-10-12T17:28:04Z
---

# Introducción

Statusfy es un Sistema de Página de Estado, fácil de usar y completamente de código abierto. Puedes crear fácilmente un Sistema rápido, ya sea [**Stático**](../guide/architecture.md#generacion-estatica) o [**Renderizado por Servidor**](../guide/architecture.md#srenderizado-por-servidor) e implementarlo fácilmente en una variedad de [servicios de alojamiento](../guide/deploy.md).
Expand Down
4 changes: 4 additions & 0 deletions packages/docs/src/es/guide/api.md
@@ -1,4 +1,8 @@
---
title: API
description: Statusfy es un SPA (Single Page Application o Aplicación de Página Única) que lee sus datos desde una API RESTful interna. Tu también puedes recuperar estos datos desde una aplicación o biblioteca existente que puedas estar usando.
date: 2018-10-12T17:28:04Z
permalink: /guide/api
sidebarDepth: 3
---

Expand Down
7 changes: 7 additions & 0 deletions packages/docs/src/es/guide/architecture.md
@@ -1,3 +1,10 @@
---
title: Arquitectura
description: Statusfy fue diseñado para generar un Sistema de Página de Estado que actúa como Una Aplicación Web con la arquitectura JAMstack en mente. El objetivo detrás es reducir los costos y la complejidad, proporcionando una alternativa "Serverless" más simple y versátil.
date: 2018-10-12T17:28:04Z
permalink: /guide/architecture
---

# Arquitectura

Statusfy fue diseñado para generar un Sistema de Página de Estado que actúa como Una Aplicación Web con la arquitectura [JAMstack](https://jamstack.org/) en mente. El objetivo detrás es reducir los costos y la complejidad, proporcionando una alternativa [**"Serverless"**](https://serverless.com/learn/overview/) más simple y versátil.
Expand Down
7 changes: 7 additions & 0 deletions packages/docs/src/es/guide/commands.md
@@ -1,3 +1,10 @@
---
title: Comandos
description: Statusfy viene con un conjunto de comandos útiles, tanto para fines de desarrollo como de producción. Puedes usar --help con cualquier comando para obtener un uso detallado.
date: 2018-10-12T17:28:04Z
permalink: /guide/commands
---

# Comandos

Statusfy viene con un conjunto de comandos útiles, tanto para fines de desarrollo como de producción. Puedes usar `--help` con cualquier comando para obtener un uso detallado.
Expand Down
9 changes: 9 additions & 0 deletions packages/docs/src/es/guide/configuration.md
@@ -1,5 +1,14 @@
---
title: Configuration
description: Statusfy es fácil de configurar y soporta diferentes formatos de archivo. Defines un archivo de configuración principal y el sistema hace su trabajo.
date: 2018-10-12T17:28:04Z
permalink: /guide/configuration
---

# Configuración

Statusfy es fácil de configurar y soporta diferentes formatos de archivo. Defines un archivo de configuración principal y el sistema hace su trabajo.

## Archivo de Configuración

Sin ninguna configuración, Statusfy utilizará los valores predeterminados para que funcione correctamente tu Sistema de Página de Estado. El archivo de configuración se debe colocar en la raíz de tu proyecto:
Expand Down
6 changes: 5 additions & 1 deletion packages/docs/src/es/guide/deploy.md
@@ -1,10 +1,14 @@
---
title: Despliegue
description: "Puedes entregar su Sistema de Páginas de Estado creado con Statusfy de dos maneras diferentes: Generación Estática o Renderizado por Servidor."
date: 2018-10-12T17:28:04Z
permalink: /guide/deploy
sidebarDepth: 3
---

# Despliegue

Puedes entregar su Sistema de Páginas de Estado creado con Statusfy de dos maneras diferentes:: **Generación Estática** o **Renderizado por Servidor**.
Puedes entregar su Sistema de Páginas de Estado creado con Statusfy de dos maneras diferentes: **Generación Estática** o **Renderizado por Servidor**.



Expand Down
7 changes: 7 additions & 0 deletions packages/docs/src/es/guide/directory-structure.md
@@ -1,3 +1,10 @@
---
title: Estructura de Directorios
description: Statusfy está diseñado para ser fácil de usar y organizar, teniendo en cuenta la Internacionalización, la estructura de documento recomendada es la siguiente.
date: 2018-10-12T17:28:04Z
permalink: /guide/directory-structure
---

# Estructura de Directorios

Statusfy está diseñado para ser fácil de usar y organizar, teniendo en cuenta la [Internacionalización](../guide/i18n.md), la estructura de documento recomendada es la siguiente:
Expand Down
7 changes: 7 additions & 0 deletions packages/docs/src/es/guide/getting-started.md
@@ -1,3 +1,10 @@
---
title: Primeros Pasos
description: Comenzar con Statusfy es realmente sencillo, solo tiene que centrarse en escribir su contenido y utilizar el CLI para crear y desplegar tu sitio web.
date: 2018-10-12T17:28:04Z
permalink: /guide/getting-started
---

# Primeros Pasos

Comenzar con Statusfy es realmente sencillo, solo tiene que centrarse en escribir su contenido y utilizar el [CLI](../guide/commands.md) para crear y desplegar tu sitio web.
Expand Down
4 changes: 4 additions & 0 deletions packages/docs/src/es/guide/i18n.md
@@ -1,5 +1,9 @@
---
title: Internacionalización (i18n)
description: Statusfy fue diseñado con la internacionalización en mente y tiene algunas funcionalidades integradas para proporcionar una mejor experiencia de usuario (y para los Web Crawler Bots).
date: 2018-10-12T17:28:04Z
sidebarDepth: 3
permalink: /guide/i18n
---

# Internacionalización
Expand Down
4 changes: 4 additions & 0 deletions packages/docs/src/es/guide/incidents.md
@@ -1,5 +1,9 @@
---
title: Incidentes
description: "Los incidentes son el núcleo de Statusfy: no hay un sistema de página de estado sin un registro de incidentes. La información de incidentes se almacena en un archivo de Markdown con atributos y un contenido que proporciona información adicional a sus usuarios."
date: 2018-10-12T17:28:04Z
sidebarDepth: 3
permalink: /guide/incidents
---

# Incidentes
Expand Down
7 changes: 7 additions & 0 deletions packages/docs/src/es/guide/notifications.md
@@ -1,3 +1,10 @@
---
title: Notificaciones
description: Las notificaciones son una forma de mantener a sus usuarios/clientes notificados con cualquier actualización de Incidentes que pueda tener tu Sistema. Los espectadores de su página de estado pueden acceder a las siguientes opciones haciendo clic en el botón Suscribirse.
date: 2018-10-12T17:28:04Z
permalink: /guide/notifications
---

# Notificaciones <Badge text="0.2.0+"/>

Las notificaciones son una forma de mantener a sus usuarios/clientes notificados con cualquier actualización de Incidentes que pueda tener tu Sistema. Los espectadores de su página de estado pueden acceder a las siguientes opciones haciendo clic en el botón Suscribirse.
Expand Down

0 comments on commit c31c107

Please sign in to comment.