Jinsi ya kusakinisha Discourse kwenye VPS kwa Docker
Pata mwongozo kamili wa kusakinisha Discourse kwenye VPS kwa kutumia Docker. Jifunze kusanidi app.yml, SMTP, TLS, na kutatua hitilafu za RAM ili kuepuka usumbufu wa ujenzi.
Kusakinisha Discourse kwenye VPS: kontena moja, faili moja la usanidi
Ili kusakinisha Discourse kwenye VPS, unaendesha kisakinishi cha mradi wenyewe, unajibu maswali machache ya mchawi wa usanidi, na kusubiri ujenzi ukamilike. Discourse inatolewa kama kontena moja la Docker linaloshikilia programu ya Rails, PostgreSQL, Redis na nginx. Kila kitu utakachobadilisha baadaye kinapatikana katika faili moja, /var/discourse/containers/app.yml, na kila mabadiliko hufika kwenye tovuti kupitia ujenzi upya (rebuild).
Usakinishaji rasmi ni discourse_docker: hati ya shell ya launcher pamoja na seti ya violezo vya YAML. Discourse haitumii faili ya Compose unayoiandika wewe mwenyewe, na kontena hilo halijakusudiwa kutenganishwa kwa mikono. Ikiwa umezoea kuendesha huduma kwenye VPS kwa kutumia Docker Compose, tarajia muundo tofauti. Hakuna docker compose up -d hapa, na ./launcher rebuild app ndiyo njia ya kupeleka (deploy) mabadiliko.
Mahitaji ya Discourse kabla ya kuanza
Kuna mahitaji manne ambayo huwasumbua watu wengi, na kila moja hujitokeza kabla hata hujafika kwenye ukurasa wa kuingia (login).
- Kumbukumbu (RAM). Container moja huendesha PostgreSQL, Redis, Sidekiq na seva ya wavuti ya Ruby. Hatua ya ujenzi (build) hukusanya assets na inahitaji kumbukumbu zaidi kuliko tovuti inayofanya kazi.
- Jina halisi la domain. Mfano wa usanidi uliotolewa unasema wazi: "Discourse haitafanya kazi kwa kutumia namba ya IP pekee."
- Njia ya kutuma barua pepe. Uamilishaji wa akaunti, uwekaji upya wa nywila, mialiko ya admin na barua pepe za muhtasari (digest) zote hutumwa kupitia SMTP (simple mail transfer protocol).
- Port 80 na 443 lazima ziwe wazi kwenye host, isipokuwa kama utaamua kwa makusudi kuweka Discourse nyuma ya proxy unayoiendesha tayari.
The data behind this chart
[
{
"label": "Documented minimum",
"ram_gb": 1,
"storage_gb": 10
},
{
"label": "Documented recommended",
"ram_gb": 2,
"storage_gb": 20
}
]Hati rasmi ya usakinishaji inaweka kiwango cha chini cha 1 GB ya RAM pamoja na swap na 10 GB ya diski, na inapendekeza 2 GB ya RAM na 20 GB ya diski. Soma mstari wa kwanza kama namba inayoruhusu kisakinishi kumaliza kazi, si namba unayotaka ili kuendesha jamii (community). Pengo hili ni muhimu kwa sababu kilele cha matumizi ya kumbukumbu hutokea wakati wa ujenzi (build), si wakati wa trafiki ya watumiaji.
Elekeza domain kwenye seva kabla ya kusakinisha
Tengeneza A record kwa ajili ya hostname utakayotumia, kisha ithibitishe kutoka kwenye seva yenyewe.
dig +short forum.example.com
curl -4 -s https://ifconfig.coAmri zote mbili lazima zionyeshe anwani ileile. Ni lazima zikubaliane kwa sababu wizard ya usanidi hufanya jaribio la muunganisho dhidi ya hostname yako, na record inayoelekeza kwingine itafeli jaribio hilo. Record uliyotengeneza dakika mbili zilizopita inaweza kuwa bado imehifadhiwa kwenye cache, kwa hivyo subiri TTL (time to live) ya zamani ipite badala ya kupambana na wizard.
Amua sasa kama record hiyo itapitia CDN. Record inayopitia proxy huficha anwani ya seva yako, na ombi la cheti cha container litafeli, kwa sababu changamoto ya ACME (automatic certificate management environment) hujibiwa na proxy badala ya Discourse. Acha record iwe bila proxy wakati wa usakinishaji wa kwanza.
Endesha kisakinishi rasmi
Amri moja husakinisha git, husakinisha Docker kwa kutumia hati rasmi ya usakinishaji ya Docker, hufanya clone ya discourse_docker kwenye /var/discourse, na kuanzisha mchawi wa usanidi.
wget -qO- https://raw.githubusercontent.com/discourse/discourse_docker/main/install-discourse | sudo bashIkiwa Docker tayari ipo kwenye seva na ungependa kuona kila hatua, fanya kazi hiyo hiyo kwa mikono.
sudo -s
git clone https://github.com/discourse/discourse_docker.git /var/discourse
cd /var/discourse
./discourse-setupIendeshe kama root. Ikianzishwa kama mtumiaji wa kawaida, discourse-setup husimama mara moja na This script must be run as root. Please sudo or log in as root first.. Bila Docker kwenye seva, husimama na Docker is not installed. Please install Docker first., kwa sababu clone ya mikono haikusakinishi chochote.
Mambo yanayoulizwa na wizard ya usanidi, na inayoandika
Kufikia Agosti 2026, discourse-setup ni kanga nyepesi (thin wrapper). Inaendesha discourse/setup-wizard:release kama container ikiwa na mtandao wa host na Docker socket iliyowekwa (mounted), ili wizard iweze kukagua mashine inayosanidi. Inauliza hostname na anwani za barua pepe za admin, kisha block yako ya SMTP. Inaandika containers/app.yml, kisha inajenga upya (rebuild).
Tabia mbili zinafaa kujulikana kabla ya kuanza. Ikiwa mashine haina kumbukumbu ya kutosha na haina swap, wizard husimama na kutoa ofa ya kuitengeneza: wrapper hiyo hutengeneza /swapfile ya 2 GB, inaiongeza kwenye /etc/fstab, inaweka vm.swappiness = 10 kwenye /etc/sysctl.d/30-discourse-swap.conf, na kuanzisha wizard tena. Wizard inapomaliza, inachapisha Rebuilding app in 5 seconds (Ctrl+C to cancel)... na kuendesha ./launcher rebuild app kwenye host. Ujenzi huo huchukua dakika kadhaa kwenye VPS ndogo, na ujenzi wa kwanza ndio wa polepole zaidi kwa sababu kila asset inakusanywa (compiled) kuanzia mwanzo.
./discourse-setup --help inaorodhesha flag muhimu wakati kitu fulani hakiendi sawa. --skip-rebuild inaandika usanidi bila kujenga, na --skip-connection-test inaruka ukaguzi wa DNS na port. Tumia --skip-connection-test tu wakati tayari unajua kwa nini jaribio linashindwa, kwa mfano wakati host iko nyuma ya firewall ya mtandao unayoimiliki.
Soma app.yml kabla ya ujenzi wa kwanza
Mchawi (wizard) hutengeneza faili ambalo sasa ni jukumu lako kulisimamia. Lifungue kwa kutumia sudo nano /var/discourse/containers/app.yml. Hizi ndizo sehemu zinazoamua karibu kila kitu.
templates:
- "templates/postgres.template.yml"
- "templates/redis.template.yml"
- "templates/web.template.yml"
- "templates/web.ratelimited.template.yml"
## Uncomment these two lines if you wish to add Lets Encrypt (https)
#- "templates/web.ssl.template.yml"
#- "templates/web.letsencrypt.ssl.template.yml"
expose:
- "80:80" # http
- "443:443" # https
env:
DISCOURSE_HOSTNAME: "forum.example.com"
DISCOURSE_DEVELOPER_EMAILS: "you@example.com"
DISCOURSE_SMTP_ADDRESS: smtp.example.com
DISCOURSE_SMTP_PORT: 587
DISCOURSE_SMTP_USER_NAME: user@example.com
DISCOURSE_SMTP_PASSWORD: "your-smtp-password"DISCOURSE_HOSTNAME ndilo anwani ambalo tovuti hujibu kupitia hilo, na Discourse hujenga viungo vyake kulingana na anwani hiyo, kwa hivyo thamani isiyo sahihi itakupa tovuti inayopakia mara moja kisha kukupeleka mahali pengine. DISCOURSE_DEVELOPER_EMAILS ni orodha iliyotenganishwa kwa koma, na anwani hizo huwa admin moja kwa moja wakati wa usajili wa kwanza. Weka anwani yako hapo na ujisajili nayo, kwa sababu ndivyo akaunti ya kwanza ya admin inavyoundwa.
Faili hili huhifadhi nenosiri lako la SMTP katika maandishi wazi (plain text), kwa hivyo zuia saraka hiyo kwa kutumia sudo chmod 700 /var/discourse/containers. Pia ni YAML, ambayo inamaanisha nafasi nyeupe (whitespace) ni usanidi: ufunguo uliopangwa vibaya husababisha ujenzi kufeli kwa hitilafu ya uchanganuzi (parse error) na kukuacha bila tovuti. Mtego mmoja umeandikwa katika faili la sampuli lenyewe. # ndani ya nenosiri lisilowekwa kwenye alama za kunukuu huanzisha maoni (comment), kwa hivyo weka alama za kunukuu kwenye nenosiri lolote lenye alama hiyo.
Baruapepe ndiyo hatua inayokwamisha usakinishaji mwingi
Kufikia Agosti 2026, mchawi wa usakinishaji hukuruhusu kuruka SMTP na kutumia akaunti za Discourse ID badala yake, na app.yml inabeba swichi inayolingana ya DISCOURSE_SKIP_EMAIL_SETUP, iliyoelezwa hapo kama kuruka uthibitishaji wa usanidi wa baruapepe. Kuruka hatua hii ni sawa kwa ajili ya kuangalia programu kwa mara ya kwanza. Ni chaguo mbaya kwa jumuiya, kwa sababu bila baruapepe kutoka nje, hakuna mtu anayeweza kuamilisha akaunti au kubadilisha nenosiri.
Tatizo la kivitendo ni kwamba watoa huduma wengi wa VPS huzuia port 25 ya kutoka, kwa hivyo seva ya kawaida ya baruapepe kwenye mashine hiyo haitaleta ujumbe. Tumia relay iliyothibitishwa kwenye port 587, au kwenye 465 yenye TLS (transport layer security) ya moja kwa moja. Kwa 465, weka DISCOURSE_SMTP_FORCE_TLS: true, ambayo usanidi wa sampuli unapendekeza kwa port hiyo. Jaribu uwezo wa kufikia (reachability) kutoka kwa seva pangishi kabla ya kujenga upya.
nc -vz smtp.example.com 587Matokeo mazuri ni mstari mmoja unaoishia na succeeded!. Amri inayokwama na kisha kuisha muda wake inamaanisha kuwa port imezuiwa kwenye njia ya kutoka ya VPS yako, na hakuna mpangilio wa Discourse unaoweza kurekebisha hilo. Hamia kwenye port ambayo mtoa huduma wako anaruhusu, au mwombe mtoa huduma aifungue.
Tovuti ikishafanya kazi, tuma ujumbe wa majaribio kutoka ukurasa wa Email katika sehemu ya Admin, kisha soma vichupo vya Skipped na Bounced kwenye ukurasa huo huo. Vichupo hivyo ndipo Discourse hurekodi baruapepe iliyokataa kutuma na baruapepe iliyokataliwa na relay, na huonyesha sababu, jambo ambalo ni la haraka zaidi kuliko kusoma logi.
TLS: acha kontena ipate cheti chake chenyewe
Ikiwa Discourse inamiliki port 80 na 443, tumia mfumo wake wa ndani wa kutoa vyeti. Ondoa alama ya maoni kwenye mistari miwili ya template ya SSL iliyoonyeshwa hapo juu, kisha fanya rebuild. Template hiyo huendesha acme.sh, huhifadhi vyeti kwenye volume iliyoshirikiwa chini ya /shared/ssl, huvihuisha kulingana na ratiba ndani ya kontena, na kuiweka Discourse kulazimisha HTTPS.
Port 80 lazima ibaki inafikika kutoka kwenye Internet ili hili lifanikiwe, kwa sababu changamoto ya HTTP hujibiwa hapo. Firewall inayoruhusu port 443 pekee itakupa build inayokamilika lakini cheti hakitawahi kutolewa. Angalia matokeo kwa kutumia ./launcher logs app mara tu baada ya rebuild.
Je, unapaswa kuweka nginx au Caddy mbele?
Ikiwa Discourse ndiyo huduma pekee ya wavuti kwenye VPS, usifanye hivyo. Kontena hilo tayari linaendesha nginx iliyosanidiwa vyema, na proksi ya pili huongeza hatua ya ziada, cheti kingine cha kuhuisha, na chanzo kipya cha hitilafu za header.
Iweke mbele ikiwa VPS hiyo hiyo inahudumia tovuti nyingine. Ongeza templates/web.socketed.template.yml kwenye orodha ya templates, toa maoni (comment out) kwenye mistari yote miwili ya expose, na uache templates mbili za SSL zikiwa zimefungwa kwa maoni. Kontena hilo kisha husikiliza kwenye unix socket katika /var/discourse/shared/standalone/nginx.http.sock na halishiki port yoyote, jambo linaloacha port 80 na 443 wazi kwa proksi yako mwenyewe.
server {
listen 443 ssl;
server_name forum.example.com;
location / {
proxy_pass http://unix:/var/discourse/shared/standalone/nginx.http.sock:;
proxy_set_header Host $http_host;
proxy_http_version 1.1;
proxy_set_header X-Forwarded-For $remote_addr;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Real-IP $remote_addr;
}
}Koloni la mwisho baada ya .sock ni sehemu ya sintaksia ya unix socket ya nginx, na sudo nginx -t hukataa usanidi huo bila koloni hilo. X-Forwarded-Proto si ya hiari pia. Discourse huandika viungo kamili (absolute links), kwa hivyo bila header hiyo hutoa viungo vya http:// kwenye ukurasa wa HTTPS, na vivinjari huvizuia kama maudhui mchanganyiko (mixed content). Kontena likiwa kwenye socket, TLS inakuwa jukumu lako, kwa hivyo toa cheti kwenye host kwa kutumia Certbot kwenye Ubuntu 24.04 na nginx. Ikiwa bado hujaamua kuhusu proksi, ulinganisho wa nginx, Caddy na Traefik unaelezea mabadilishano unayofanya.
Ujenzi upya, maboresho na amri utakazotumia kikamilifu
cd /var/discourse
./launcher rebuild apprebuild huharibu container inayofanya kazi, huandaa mpya kutoka app.yml, na kuianzisha. Tovuti huwa nje ya mtandao wakati wote wa ujenzi, kwa hivyo chukulia kila mabadiliko ya usanidi kama muda wa matengenezo uliopangwa wa dakika chache.
Kubadilisha thamani pekee zilizo chini ya env: hakuhitaji hatua hiyo. ./launcher destroy app && ./launcher start app hutengeneza upya container kutoka kwenye image uliyokwisha ijenga, jambo linalochukua sekunde chache. Chochote kilicho chini ya templates: au hooks: hubadilisha image yenyewe, kwa hivyo inahitaji ujenzi upya kamili.
Maboresho hufika kwa njia mbili. Point releases hutumika kutoka kwenye kiolesura cha wavuti katika /admin/upgrade, zinazotolewa na plugin ya docker_manager ambayo app.yml hu-clone wakati wa ujenzi. Mabadiliko kwenye base image au templates hutoka kwenye git.
cd /var/discourse
git pull
./launcher rebuild appUjenzi upya ndipo seva ndogo hushindwa, kwa sababu mkusanyiko wa asset (asset compilation) ndio kilele cha matumizi ya kumbukumbu (memory) kwa mfumo mzima. Ujenzi unaokwama katikati, huku dmesg ikionyesha mstari kama Out of memory: Killed process unaotaja mchakato wa ruby, ulikosa kumbukumbu wakati wa ujenzi ingawa tovuti yenyewe ilikuwa ikifanya kazi vizuri awali. Ongeza swap na uendeshe ujenzi upya tena.
./launcher logs app
./launcher enter app
./launcher cleanuplogs huchapisha matokeo ya container, enter hufungua shell ndani yake, na cleanup huondoa container zilizosimamishwa kwa zaidi ya saa 24. Endesha cleanup mara kwa mara, kwa sababu kila ujenzi upya huacha container ya zamani nyuma na diski kwenye VPS ndogo hujaa kimya kimya.
Hifadhi rudufu (backups), na faili ambalo hifadhi hiyo halina
Chukua hifadhi rudufu kutoka kwenye ukurasa wa Backups katika Admin. Kumbukumbu hiyo huhifadhiwa kwenye seva katika /var/discourse/shared/standalone/backups/default/. Kazi hiyo hiyo inaweza kuendeshwa kutoka kwenye shell.
cd /var/discourse
./launcher enter app
discourse backupdiscourse restore <filename> huirejesha, na urejeshaji hukataliwa hadi utakapoiendesha discourse enable_restore. Kinga hiyo ipo ili amri ya bahati mbaya isifute jukwaa (forum) linalofanya kazi.
Kuna mapungufu mawili unayopaswa kuziba mwenyewe. Kumbukumbu hiyo huhifadhi hifadhidata, na huhifadhi faili zilizopakiwa (uploaded files) pale tu mpangilio wa hifadhi rudufu unaojumuisha uploads unapokuwa umewashwa, kwa hivyo hakiki mpangilio huo kabla ya kuutegemea. Hifadhi hiyo haina kamwe app.yml, kwa hivyo urejeshaji kwenye VPS mpya bado utahitaji hostname yako na block ya SMTP, jambo linalomaanisha kuwa unapaswa kunakili faili hiyo nje ya seva hiyo pia.
Pia, kumbukumbu hiyo hukaa kwenye diski ileile ya tovuti inayolindwa, jambo ambalo si hifadhi rudufu ya kweli. Ihamishe kwenda mahali pengine kwa ratiba maalum.
rsync -avz root@forum.example.com:/var/discourse/shared/standalone/backups/default/ ~/discourse-backups/Gharama ya RAM kwa jukwaa lenye shughuli nyingi
Bootstrap huweka UNICORN_WORKERS na db_shared_buffers kulingana na kumbukumbu na CPU inazotambua, na usanidi wa sampuli hupunguza shared buffers kufikia robo ya jumla ya kumbukumbu. Kila mfanyakazi wa unicorn ni mchakato kamili wa Ruby, na Sidekiq huendesha kazi za nyuma (background jobs) kando yao, kwa hivyo matumizi ya kumbukumbu hufuata maombi yanayofanyika kwa wakati mmoja badala ya idadi ya wanachama waliosajiliwa. Jukwaa tulivu lenye wanachama mia chache si mzigo mzito wa kazi. Kile kingine kinachoshiriki seva hiyo mara nyingi ni muhimu zaidi, na ikiwa ni maktaba ya picha, viwango vya chini vya RAM vilivyopimwa katika ulinganisho wa PhotoPrism na Immich vitakuambia ikiwa ujenzi upya wa Discourse bado una nafasi ya kutosha kukamilika.
Usikadirie ukubwa wa seva kulingana na namba iliyo kwenye makala, ikiwemo hii. Pima yako mwenyewe.
free -m
docker stats --no-streamSwap inayotumika kila mara pamoja na kurasa za polepole inamaanisha kuwa huna RAM ya kutosha. Kumbukumbu thabiti yenye kurasa za polepole kwa kawaida inamaanisha kitu kingine, kwa hivyo soma ./launcher logs app kabla ya kununua mpango mkubwa zaidi. Ongeza ukaguzi kutoka nje ya seva pia, kwa sababu jukwaa linalokosa kumbukumbu saa 9 usiku hushindwa kimya kimya: kifuatiliaji cha hali cha Uptime Kuma kinachojiendesha kwenye seva tofauti kitakuambia kabla ya wanachama wako kugundua.
Wakati Discourse si chaguo sahihi
Discourse ni programu kubwa yenye usakinishaji mzito na mzunguko wa rebuild kwa kila mpangilio unaopatikana katika app.yml. Gharama hiyo inakupa zana halisi za usimamizi wa maudhui na utafutaji unaofanya kazi hata wakati kumbukumbu ni kubwa. Kwa watu thelathini wanaotaka mahali pa kuzungumza, hii ni mashine kubwa kuliko mahitaji ya mazungumzo hayo. Soma ulinganisho wa programu za jukwaa zinazojiendesha (self-hosted) kwanza, na uchague Discourse kwa sababu unataka utendaji wake, si kwa sababu ni jina unalolijua tayari.
FAQ
Je, ninaweza kusakinisha Discourse kwenye VPS bila jina la kikoa (domain name)?
Hapana. Usanidi uliotolewa unaeleza kuwa Discourse haitafanya kazi kwa kutumia anwani ya IP pekee, na DISCOURSE_HOSTNAME inahitajika. Discourse hutengeneza viungo kamili (absolute links) kulingana na hostname hiyo, kwa hivyo anwani ya IP itavunja viungo na kuzuia utoaji wa cheti cha TLS. Unda A record kabla ya kuanza, na uthibitishe kwa kutumia dig +short forum.example.com kuwa inaelekeza kwenye anwani ya seva yako.
Je, lazima nisanidi SMTP ili kukamilisha usakinishaji?
Kufikia Agosti 2026 unaweza kuruka hatua hii. Mchawi wa usanidi (setup wizard) hutoa chaguo la kuingia kwa kutumia Discourse ID badala yake, na app.yml ina flag inayoruhusu kuruka uthibitishaji wa barua pepe. Kwa matumizi yoyote zaidi ya majaribio ya awali, sanidi SMTP, kwa sababu uanzishaji wa akaunti na uwekaji upya wa nywila hutegemea barua pepe. Tumia relay iliyothibitishwa (authenticated relay) kwenye port 587 au 465, kwa kuwa watoa huduma wengi wa VPS huzuia trafiki ya nje kwenye port 25.
Kwa nini ujenzi (rebuild) wa Discourse umefeli katikati?
Kumbukumbu (memory) ndiyo sababu ya kawaida. Uundaji wa faili za asset wakati wa ujenzi unahitaji kumbukumbu nyingi kuliko tovuti inayoendeshwa, kwa hivyo seva inayoweza kuhudumia jukwaa vizuri inaweza kushindwa wakati wa rebuild. Ikiwa dmesg inaonyesha Out of memory: Killed process ikitaja mchakato wa ruby, ongeza swap (swapfile ya mchawi wa usanidi ni 2 GB) na uendeshe ./launcher rebuild app tena. Ujenzi unaokwama kwenye hitilafu ya YAML unaashiria kosa la mpangilio (indentation) katika app.yml.
Je, Discourse inapaswa kukaa nyuma ya nginx au Caddy yangu mwenyewe?
Ni pale tu VPS inapohudumia tovuti nyingine pia. Ikiwa pekee yake kwenye seva, acha container ishike port 80 na 443 na itoe cheti chake yenyewe, jambo linalopunguza vipengele vya ziada. Ili kushiriki mashine, ongeza templates/web.socketed.template.yml, toa maoni (comment out) kwenye mistari ya expose, na uelekeze trafiki (proxy) kwenye unix socket iliyo kwenye /var/discourse/shared/standalone/nginx.http.sock. Pitisha X-Forwarded-Proto, vinginevyo Discourse itatoa viungo vya http:// kwenye ukurasa wa HTTPS.
Ninawezaje kuhifadhi nakala (backup) ya Discourse inayojiendesha yenyewe?
Tumia ukurasa wa Backups katika sehemu ya Admin, au endesha discourse backup baada ya ./launcher enter app. Kumbukumbu (archives) huhifadhiwa kwenye seva katika /var/discourse/shared/standalone/backups/default/. Thibitisha kuwa mpangilio unaojumuisha uploads umewashwa, nakili /var/discourse/containers/app.yml pamoja na kumbukumbu hiyo, na uihamishe kwenye mashine nyingine, kwa sababu nakala iliyopo kwenye diski moja na tovuti haitasaidia ikiwa diski hiyo itafeli.