aboutsummaryrefslogtreecommitdiff
path: root/src/layouts/BlogSingleLayout.astro
diff options
context:
space:
mode:
authorAriel Costas Guerrero <ariel@costas.dev>2025-06-07 20:17:01 +0200
committerAriel Costas Guerrero <ariel@costas.dev>2025-06-07 20:17:01 +0200
commit6cb688bd1b2285fb917194852fdc285c798d43cc (patch)
tree535293539e53dfa3ec3aeca8f217b6d066350c75 /src/layouts/BlogSingleLayout.astro
parent36d3a2c4c6dbfcc74271d0956eff9b1e454fc138 (diff)
Add new images and update portfolio layouts for enhanced presentation
Diffstat (limited to 'src/layouts/BlogSingleLayout.astro')
-rw-r--r--src/layouts/BlogSingleLayout.astro134
1 files changed, 134 insertions, 0 deletions
diff --git a/src/layouts/BlogSingleLayout.astro b/src/layouts/BlogSingleLayout.astro
new file mode 100644
index 0000000..0c3b934
--- /dev/null
+++ b/src/layouts/BlogSingleLayout.astro
@@ -0,0 +1,134 @@
+---
+import Layout from "@/layouts/Layout.astro";
+import { getCollection, render } from "astro:content";
+import { type GetStaticPaths } from "astro";
+
+interface Props {
+ entry: any;
+}
+
+export const getStaticPaths: GetStaticPaths = async () => {
+ const entries = await getCollection("blog");
+ return entries.map((entry: any) => ({
+ params: { id: entry.id },
+ props: { entry },
+ }));
+};
+
+const { entry } = Astro.props;
+const { Content } = await render(entry);
+const formattedDate = new Date(entry.data.publishedAt).toLocaleDateString(
+ "es-ES",
+ {
+ year: "numeric",
+ month: "long",
+ day: "numeric",
+ weekday: "long",
+ },
+);
+
+const schema = {
+ "@context": "https://schema.org",
+ "@type": "BlogPosting",
+ headline: entry.data.title,
+ datePublished: entry.data.publishedAt.toISOString(),
+ keywords: entry.data.tags || [],
+ author: {
+ "@type": "Person",
+ name: "Ariel Costas Guerrero",
+ },
+ publisher: {
+ "@type": "Person",
+ name: "Ariel Costas Guerrero",
+ url: "https://www.costas.dev",
+ image: {
+ "@type": "ImageObject",
+ url: "https://www.costas.dev/favicon.png",
+ },
+ },
+};
+---
+
+<Layout title={entry.data.title} description={entry.data.metaDescription}>
+ <script
+ is:inline
+ type="application/ld+json"
+ slot="head-jsonld"
+ set:html={JSON.stringify(schema)}
+ />
+
+ <h1>{entry.data.title}</h1>
+ <small>
+ Publicado el
+ <time datetime={entry.data.publishedAt.toISOString()}>
+ {formattedDate}
+ </time>
+ {entry.data.tags && entry.data.tags.length > 0 && (
+ <>
+ • Etiquetas:
+ <ul class="tags">
+ {entry.data.tags.map((tag: string) => (
+ <li><a href={`/blog/?tag=${encodeURIComponent(tag)}`}>{tag}</a></li>
+ ))}
+ </ul>
+ </>
+ )}
+ </small>
+
+ <Content />
+
+ <p>
+ <a href="/blog">Volver al blog</a>
+ </p>
+</Layout>
+
+<style lang="scss">
+ @use "../../styles/variables" as v;
+ @use "sass:color";
+
+ .tags {
+ display: inline-flex;
+ list-style: none;
+ margin: 0;
+ padding: 0;
+ gap: 0.75rem;
+ }
+
+ .tags li {
+ display: inline;
+ }
+
+ .tags a {
+ // Estilo de enlace normal, siguiendo los estilos predefinidos en Layout.astro
+ color: v.$accentDark;
+ font-size: 0.85rem;
+ font-family: v.$monoFontStack;
+ text-decoration: none;
+ box-shadow: 0 1px v.$accent;
+ transition: all 0.2s ease;
+
+ &:hover {
+ box-shadow: 0 2px v.$accentDark;
+ }
+
+ &:focus {
+ color: v.$accentDark;
+ outline: none;
+ background-color: v.$secondary;
+ box-shadow: 0 4px #0b0c0c;
+ }
+ }
+
+ /* Estilos para la información de la publicación */
+ small {
+ display: block;
+ margin-top: -1rem;
+ margin-bottom: 1.5rem;
+ font-size: 0.85rem;
+ color: color.adjust(v.$dark, $lightness: 30%);
+ }
+
+ time {
+ font-style: italic;
+ }
+</style>