ساخت وبسایت رایگان با Hugo و Codeberg Pages
ساخت وبسایت رایگان با Hugo و Codeberg Pages
اگر دنبال یک وبسایت شخصی، وبلاگ یا صفحه پروژه هستید، لزوماً لازم نیست سراغ هاست پولی، WordPress یا سرویسهای پیچیده بروید.
با ترکیب Hugo، Git و Codeberg Pages میتوان یک وبسایت استاتیک را کاملاً رایگان منتشر کرد.
در این روش، سایت روی سیستم خودمان ساخته میشود، کد و محتوای آن در Codeberg قرار میگیرد و با هر git push، سایت به صورت خودکار ساخته و منتشر میشود.
در این آموزش از Arch Linux استفاده میکنم، ولی بیشتر دستورات روی توزیعهای دیگر لینوکس هم مشابه هستند.
چیزهایی که نیاز داریم
برای این روش به این موارد نیاز داریم:
- یک حساب Codeberg
- Git
- Hugo
- یک ترمینال
- یک repository در Codeberg
- کمی حوصله
سایت نهایی هم میتواند بدون پرداخت هزینهای روی دامنهای مثل این قرار بگیرد:
https://username.codeberg.page/
اگر repository شما pages باشد، این آدرس به عنوان سایت اصلی حساب شما استفاده میشود.
مثلاً:
https://delta-fsociety.codeberg.page/
Codeberg برای سایت کاربر یا سازمانی دقیقاً همین الگو را دارد و repository باید pages نام داشته باشد.
۱. نصب Hugo
در Arch Linux میتوانیم Hugo را مستقیماً از repository نصب کنیم:
sudo pacman -S hugo
بعد بررسی میکنیم که نصب شده باشد:
hugo version
مثلاً:
hugo v0.166.0
خود Hugo برای بررسی نصب، دستور hugo version را پیشنهاد میکند.
۲. ساخت پروژه Hugo
یک پوشه برای سایت ایجاد میکنیم:
mkdir ~/pages
cd ~/pages
حالا پروژه Hugo را ایجاد میکنیم:
hugo new site .
بعد ساختار اولیه پروژه را داریم:
pages/
├── archetypes/
├── assets/
├── content/
├── data/
├── layouts/
├── static/
├── themes/
└── hugo.toml
مهمترین بخشها:
content/
محتوای سایت در اینجا قرار میگیرد.
layouts/
قالب HTML سایت در اینجا قرار میگیرد.
static/
فایلهای استاتیک مثل عکس، favicon و CSSهای ساده میتوانند اینجا باشند.
hugo.toml
تنظیمات اصلی سایت است.
۳. ساخت اولین پست
برای ساخت اولین نوشته:
hugo new posts/hello-world.md
فایل ساختهشده را باز میکنیم:
nano content/posts/hello-world.md
مثلاً:
---
title: "سلام دنیا"
date: 2026-09-19
draft: false
---
# سلام دنیا
این اولین پست وبلاگ من است.
این سایت با Hugo ساخته شده و روی Codeberg Pages میزبانی میشود.
نکته مهم این است که:
draft: false
باشد.
اگر draft روی true باشد، نوشته در build معمولی منتشر نمیشود.
۴. اجرای سایت روی سیستم خودمان
قبل از اینکه سایت را روی اینترنت منتشر کنیم، بهتر است آن را محلی ببینیم.
hugo server
Hugo معمولاً یک آدرس مانند این میدهد:
http://localhost:1313/
آن را در مرورگر باز کنید.
هر تغییری که در محتوا ایجاد کنید، Hugo میتواند صفحه را به صورت خودکار reload کند.
برای متوقف کردن server:
Ctrl + C
۵. اضافه کردن Theme
Hugo خودش موتور ساخت سایت است و برای ظاهر سایت میتوان از theme استفاده کرد.
Themeها را میتوان به شکلهای مختلف به پروژه اضافه کرد.
یکی از روشها استفاده از Hugo Modules است.
مثلاً اگر یک theme از Hugo Modules استفاده کند، ابتدا:
hugo mod init codeberg.org/username/pages
بعد dependency مورد نظر را دریافت میکنیم.
مثلاً:
hugo mod get github.com/cebor/vellum
بعد Hugo میتواند dependency را هنگام build مدیریت کند.
نکته مهم این است که دستور hugo mod init را فقط یک بار برای پروژه انجام میدهیم.
۶. ساخت Git repository
حالا پروژه را تبدیل به Git repository میکنیم:
git init
بررسی:
git status
بهتر است public/ را وارد Git نکنیم.
Hugo هنگام build خودش این پوشه را ایجاد میکند.
یک فایل .gitignore بسازید:
nano .gitignore
و داخل آن:
/public/
/resources/_gen/
.hugo_build.lock
دلیلش این است که public/ خروجی تولیدشده Hugo است و نباید آن را دستی داخل repository نگه داریم.
۷. ساخت repository در Codeberg
وارد Codeberg شوید و یک repository جدید بسازید.
برای سایت اصلی حساب، نام repository باید:
pages
باشد.
مثلاً repository من:
https://codeberg.org/delta-fsociety/pages
است.
repository را public کنید.
۸. اتصال Git به Codeberg
میتوانیم repository را با HTTPS متصل کنیم، ولی برای کار روزمره SSH راحتتر است.
مثلاً remote:
ssh://git@codeberg.org/delta-fsociety/pages.git
برای تنظیم remote:
git remote add origin ssh://git@codeberg.org/delta-fsociety/pages.git
بررسی:
git remote -v
باید چیزی شبیه این ببینیم:
origin ssh://git@codeberg.org/delta-fsociety/pages.git (fetch)
origin ssh://git@codeberg.org/delta-fsociety/pages.git (push)
۹. استفاده از SSH بدون خراب کردن GitHub
اگر از قبل برای GitHub کلید SSH دارید، لازم نیست همان کلید را برای Codeberg استفاده کنید.
اتفاقاً میتوانیم برای هر سرویس کلید جدا داشته باشیم.
مثلاً کلید Codeberg:
ssh-keygen -t ed25519 -a 100 \
-f ~/.ssh/id_ed25519_codeberg \
-C "delta@codeberg"
حالا:
~/.ssh/id_ed25519_codeberg
~/.ssh/id_ed25519_codeberg.pub
ساخته میشود.
کلید عمومی را ببینید:
cat ~/.ssh/id_ed25519_codeberg.pub
محتوای آن را در:
Codeberg
→ Settings
→ SSH / GPG Keys
→ Add Key
اضافه کنید.
کلید خصوصی را به هیچکس ندهید.
۱۰. تنظیم SSH برای Codeberg
فایل SSH config:
nano ~/.ssh/config
مثلاً:
Host github.com
Hostname ssh.github.com
Port 443
User git
IdentityFile ~/.ssh/id_ed25519
IdentitiesOnly yes
Host codeberg.org
Hostname codeberg.org
Port 22
User git
IdentityFile ~/.ssh/id_ed25519_codeberg
IdentitiesOnly yes
در این حالت:
github.com
از:
~/.ssh/id_ed25519
استفاده میکند.
و:
codeberg.org
از:
~/.ssh/id_ed25519_codeberg
استفاده میکند.
بنابراین تنظیم GitHub دستنخورده باقی میماند.
برای تست Codeberg:
ssh -T git@codeberg.org
اگر authentication موفق باشد، Codeberg به شما اطلاع میدهد که احراز هویت انجام شده، ولی shell access ارائه نمیکند.
۱۱. اولین commit
حالا فایلها را اضافه میکنیم:
git add .
بررسی:
git status
بعد:
git commit -m "Initial Hugo website"
۱۲. Push کردن به Codeberg
شاخه اصلی ما main است:
git branch -M main
حالا:
git push -u origin main
از این به بعد معمولاً فقط:
git push
کافی است.
۱۳. فعال کردن Codeberg Actions
حالا باید deployment خودکار را فعال کنیم.
در repository بروید به:
Settings
→ Units
→ Overview
و:
Actions
را فعال کنید.
Codeberg Actions به صورت پیشفرض برای repositoryها فعال نیست.
۱۴. ساخت workflow
داخل پروژه این مسیر را بسازید:
mkdir -p .forgejo/workflows
حالا:
nano .forgejo/workflows/deploy.yml
یک workflow ساده برای Hugo میتواند به این شکل باشد:
name: Deploy Hugo
on:
push:
branches:
- main
jobs:
deploy:
runs-on: codeberg-small
steps:
- name: Checkout
uses: actions/checkout@v7
- name: Install Hugo
run: |
HUGO_VERSION=0.166.0
mkdir -p "${HOME}/.local/hugo"
curl -sfL \
"https://github.com/gohugoio/hugo/releases/download/v${HUGO_VERSION}/hugo_${HUGO_VERSION}_linux-amd64.tar.gz" \
-o /tmp/hugo.tar.gz
tar -C "${HOME}/.local/hugo" -xzf /tmp/hugo.tar.gz
echo "${HOME}/.local/hugo" >> "${FORGEJO_PATH}"
- name: Build
run: |
hugo build --minify
- name: Deploy
uses: actions/git-pages@v2
with:
site: https://${{ forgejo.event.repository.owner.username }}.codeberg.page/
token: ${{ forgejo.token }}
source: public/
در این workflow اتفاقات زیر میافتد:
Git push
↓
Codeberg Actions
↓
Checkout repository
↓
Install Hugo
↓
hugo build
↓
public/
↓
git-pages
↓
Codeberg Pages
Codeberg و مستندات رسمی Hugo در حال حاضر همین مدل deployment مستقیم با Git Pages Action را برای Hugo پیشنهاد میکنند. (Codeberg Documentation)
۱۵. چرا public/؟
وقتی این را اجرا میکنیم:
hugo build
Hugo سایت نهایی را داخل:
public/
میسازد.
مثلاً:
public/
├── index.html
├── posts/
├── categories/
├── tags/
├── sitemap.xml
└── index.xml
بنابراین در deployment میگوییم:
source: public/
یعنی:
محتوای تولیدشده سایت را از این پوشه منتشر کن.
خود Hugo هم توصیه میکند محتوای public/ را به repository commit نکنیم، چون این پوشه هنگام build دوباره ساخته میشود. (Hugo)
۱۶. Commit کردن workflow
حالا:
git add .forgejo/workflows/deploy.yml
بعد:
git commit -m "Add Hugo deployment workflow"
و:
git push
حالا Codeberg باید workflow را اجرا کند.
در repository:
Actions
را باز کنید.
اگر همه چیز درست باشد، یک run جدید میبینید.
۱۷. اگر workflow اجرا نشد
اول بررسی کنید Actions فعال باشد:
Settings
→ Units
→ Overview
→ Actions
بعد مطمئن شوید فایل دقیقاً اینجا قرار دارد:
.forgejo/workflows/deploy.yml
و branch شما:
main
است.
همچنین workflow باید این trigger را داشته باشد:
on:
push:
branches:
- main
یعنی هر بار که چیزی به main push شود، deployment شروع میشود.
۱۸. Trigger دستی برای تست
اگر workflow را قبلاً push کردهاید ولی Actions بعداً فعال شده، ممکن است push قبلی run نداشته باشد.
در این حالت میتوانیم یک commit خالی ایجاد کنیم:
git commit --allow-empty -m "Trigger Hugo deployment"
و:
git push
حالا باید یک run جدید در Actions ایجاد شود.
۱۹. آدرس نهایی سایت
چون repository ما نام:
pages
دارد، سایت در root دامنه Codeberg Pages منتشر میشود:
https://username.codeberg.page/
مثلاً:
https://delta-fsociety.codeberg.page/
اگر repository اسم دیگری داشت، URL معمولاً به شکل زیر بود:
https://username.codeberg.page/repository-name/
بنابراین نام pages برای سایت اصلی حساب اهمیت دارد. (Codeberg Documentation)
۲۰. از این به بعد چه اتفاقی میافتد؟
از اینجا به بعد workflow ما کاملاً ساده میشود.
مثلاً یک پست جدید میسازیم:
hugo new posts/linux.md
آن را ویرایش میکنیم:
nano content/posts/linux.md
بعد:
git add .
git commit -m "Add Linux post"
git push
و تمام.
بعد از push:
Git
↓
Codeberg
↓
Forgejo Actions
↓
Hugo
↓
public/
↓
git-pages
↓
Website
سایت به صورت خودکار بهروزرسانی میشود.
۲۱. ساختار نهایی پروژه
در نهایت پروژه ما تقریباً چنین ساختاری دارد:
pages/
├── .forgejo/
│ └── workflows/
│ └── deploy.yml
│
├── archetypes/
│
├── assets/
│
├── content/
│ └── posts/
│ ├── hello-world.md
│ └── linux.md
│
├── layouts/
│
├── static/
│
├── themes/
│
├── .gitignore
├── go.mod
├── go.sum
└── hugo.toml
پوشه:
public/
را هم معمولاً داخل Git نگه نمیداریم.
۲۲. چرا این روش جالب است؟
چون در این روش تقریباً تمام اجزای سایت تحت کنترل خودمان هستند.
محتوا:
Markdown
ساخت سایت:
Hugo
نسخهبندی:
Git
مخزن:
Codeberg
ساخت خودکار:
Forgejo Actions
انتشار:
Codeberg Pages
و مهمتر از همه، برای شروع لازم نیست هزینهای برای هاست پرداخت کنیم.
سایت استاتیک است و خبری از دیتابیس، PHP یا سرویسهای سنگین سمت سرور نیست.
۲۳. چند دستور که همیشه به کار میآیند
اجرای سایت محلی:
hugo server
ساخت سایت:
hugo build
ساخت یک پست:
hugo new posts/my-post.md
دیدن وضعیت Git:
git status
اضافه کردن تغییرات:
git add .
commit:
git commit -m "Update website"
ارسال به Codeberg:
git push
مشاهده remote:
git remote -v
تست SSH:
ssh -T git@codeberg.org
جمعبندی
برای ساخت یک وبسایت شخصی رایگان، لازم نیست حتماً یک سرویس بزرگ یا هاست پولی داشته باشیم.
یک مسیر ساده میتواند این باشد:
Hugo
+
Git
+
Codeberg
+
Forgejo Actions
+
Codeberg Pages
و workflow کلی فقط این است:
Write Markdown
↓
Git
↓
Push
↓
Codeberg Actions
↓
Hugo
↓
public/
↓
Codeberg Pages
↓
Website
این مدل برای وبلاگهای شخصی، documentation، portfolio، صفحات پروژههای FOSS و سایتهای استاتیک کوچک و متوسط کاملاً مناسب است.
و مهمتر از همه، هر چیزی که روی سایت منتشر میکنید در قالب فایلهای متنی و قابل نسخهبندی باقی میماند. یعنی اگر یک روز خواستید سرویس میزبانی را عوض کنید، محتوای اصلی سایتتان همچنان در اختیار خودتان است.
یک نکته مهم: workflow بالا را با مستندات فعلی Codeberg/Hugo هماهنگ کردم. مستندات Hugo در حال حاضر `codeberg-small` را برای workflow نمونه استفاده میکنند و Codeberg هم `git-pages/action@v2` را روش رسمی deployment معرفی کرده است. :contentReference[oaicite:4]{index=4}