How to Create a Blog with Astro


You can create a blog with Astro with a single command.

Quick and easy.

And the best part is that the static files it generates are already optimized, making the website fast.

Oh, and it’s quite recent, so it uses and/or integrates with the latest technologies.

For me, the best part is that you can create content with Markdown, so I can write from my Obsidian vault and publish with ease.

Let’s see how it’s done.

Step 1: Create the Project with Astro

To start, create a new Astro project using yarn:

yarn create astro

During the configuration process, answer the following questions:

Recommended options to configure the Astro project with yarn

  1. Where do you want to create your new project?
    • ./astro-blog-javascript (or whatever you want to name your project)
  2. How would you like to start your new project?
    • Use the blog template
  3. Do you plan to write in TypeScript?
    • No
  4. Install dependencies?
    • Yes
  5. Initialize a new git repository?
    • Yes

Note 1:

I named the project astro-blog-javascript because I wrote this article while creating the template. Replace that name with whatever suits you best.

Also, at the end of the article, I’ll explain how to use the template and get all this (and some extras I explain in other articles) right out of the box.

Note 2:

You can answer differently (of course), but I recommend using the same options as I did.

Note 3:

While writing the article, it was getting too long for my liking, and since using TypeScript or not doesn’t prevent the blog from working, I’ve separated the related actions into a subsequent article.

Step 2: Set Up the Repository

Create a new git repository:

  1. Repository name: FOLDER_NAME (in my case, astro-blog-javascript)
  2. Description: “This repository contains the main code to generate my personal website.”
  3. Mark the repository as private and leave the other options unchecked.

Navigate to the newly created project:

cd FOLDER_PROJECT # in my case `cd astro-blog-javascript/`

Set up the git remote with the repository address:

git remote add origin <address>
git branch -M main
git push -u origin main

Step 3: Make Sure Everything Works

You can do this by opening a terminal in the project folder and running:

yarn dev

and accessing http://localhost:4321/.

Note:

Check the website after each step you complete from now on to make sure everything remains the same (i.e., that you haven’t broken the website).

yarn dev automatically watches for changes and updates the website with them.

Step 4: Improve the Project Configuration

astro.config.mjs

This is Astro’s main configuration file. You should see something like the following:

import { defineConfig } from 'astro/config';
import mdx from '@astrojs/mdx';

import sitemap from '@astrojs/sitemap';

// https://astro.build/config
export default defineConfig({
    site: 'https://example.com',
    integrations: [mdx(), sitemap()],
});

Let’s extract the value of site to the src/consts.ts file to group the website’s configuration in one place, making future changes easier to manage.

After this change, the file should look like this:

import { defineConfig } from 'astro/config';
import mdx from '@astrojs/mdx';

import sitemap from '@astrojs/sitemap';

import { SITE_URL as site } from './src/consts';

// https://astro.build/config
export default defineConfig({
    site,
    integrations: [mdx(), sitemap()],
});

Note:

You’ll see that I named the constant in uppercase with underscores instead of spaces. This format is called “constant case” and is used in JavaScript/TypeScript projects to indicate that we’re using a project constant.

As you can see, there’s no problem importing it and renaming it for automatic assignment.

src/consts.ts

You’ll need to adjust the src/consts.ts file for the previous change to work properly.

After the adjustment, your src/consts.ts file should go from this:

// Place any global data in this file.
// You can import this data from anywhere in your site by using the `import` keyword.

export const SITE_TITLE = 'Astro Blog';
export const SITE_DESCRIPTION = 'Welcome to my website!';

to this:

// Place any global data in this file.
// You can import this data from anywhere in your site by using the `import` keyword.

export const SITE_TITLE = 'Astro Blog';
export const SITE_DESCRIPTION = 'Welcome to my website!';
export const SITE_URL = 'https://example.com';

tsconfig.json

Since, right now, all imports are done using relative paths, we could run into problems if we move any files to a different folder. That’s why we’re going to configure paths that can serve as absolute, so that even if we move files, the imports remain valid.

Initially, the jsconfig.json file will look like this:

{
    "extends": "astro/tsconfigs/base",
    "compilerOptions": {
        "strictNullChecks": true
    }
}

First, we’ll need to specify the base URL we’ll use. I configure it as src/ (or the default folder for the code if it’s different).

In a project created with Astro, I configure paths for all the folders from which I can import code:

  • components: folder where the code itself is stored,
  • layouts: folder where the layout elements are stored,
  • styles: folder where the style files are stored,

There are other folders (content and pages) that I consider “final,” meaning I don’t use their code in other files.

With that said, our tsconfig.ts will look like this:

{
    "extends": "astro/tsconfigs/strict",
    "compilerOptions": {
        "baseUrl": "src/",
        "paths": {
            "@/*": ["./*"],
            "@components/*": ["components/*"],
            "@layouts/*": ["layouts/*"],
            "@styles/*": ["styles/*"]
        },
        "strictNullChecks": true
    }
}

Note 1:

In many tutorials, I’ve seen people configure . (current folder) as the base URL, but in practice, this is the same as doing nothing because the URLs remain relative.

Note 2:

You might not need this much now, but if you later want to change the folder structure (e.g., to group by functionality, or to use a structure that reflects a design philosophy like “Atomic Design”), you’ll avoid many problems.

Refactor the project imports to use these shortcuts

You’ll need to change the imports in the following files:

  1. src/components/BaseHead.astro
  2. src/components/Header.astro
  3. src/components/HeaderLink.astro
  4. src/content/blog/using-mdx.mdx
  5. src/layouts/BlogPost.astro
  6. src/pages/about.astro
  7. src/pages/blog/index.astro
  8. src/pages/blog/[...slug].astro
  9. src/pages/index.astro
  10. src/pages/rss.xml

The changes you’ll need to make are:

  1. ../../components/ to @components/
  2. ../components/ to @components/
  3. ../../consts to @/consts
  4. ../consts to @/consts
  5. ../../layouts/ to @layouts/
  6. ../styles/ to @styles/

Note:

If you use an editor with functionality to replace across the entire project (like VS Code), you can use it to make these replacements globally as long as you follow the order provided.

Step 5: Apply Your Data to the Project

Update the Website Content

The blog comes with default content (which I recommend you install to have a guide on what can be done and how), but a personal blog needs… well, personal and customized content.

To do this, modify the following files:

  • src/pages/about.astro
  • src/pages/index.astro

You can also modify the following (though I recommend deleting them and creating new ones):

  • src/content/blog/first-post.md
  • src/content/blog/markdown-style-guide.md
  • src/content/blog/second-post.md
  • src/content/blog/third-post.md
  • src/content/blog/using-mdx.mdx

Finally, create as many pages or posts as you like.

Configure src/components/Header.astro to Match Your Website’s Brand

  1. Customize the menu items to show the pages you have (if you’ve changed or created new ones),
  2. Customize the list of social media links (URL, text, and icon),

Configure src/components/Footer.astro to Match Your Website’s Brand

  1. Customize the copyright line. Right now, it should say “Your name here. All rights reserved,” so change it to your name and something more,
  2. Customize the list of social media links (URL, text, and icon),

Configure src/consts.ts to Match Your Website’s Brand

  1. Update SITE_TITLE with the title you want for your blog,
  2. Update SITE_DESCRIPTION with the description you want for your blog,
    1. Keep in mind that this description is assigned to the meta tags,
  3. Update SITE_URL with the URL where your blog can be accessed,

A Little Trick

Thanks for making it this far. In upcoming articles, I’ll continue explaining how to create a custom template.

But if you don’t want to create one, you can use mine (the one you’ll have, more or less, if you follow all the steps in this series of articles) with the following command:

yarn create astro -- --template borjalofe/astro-blog-template