SSD Nodes Learn Hosting plans →
गाइड Matt Connorलेखक: Matt Connor · अपडेट किया गया: 2026-08-23

VPS पर Docker के साथ Nextcloud कैसे सेटअप करें

Docker Compose, Postgres और Redis का उपयोग करके अपने VPS पर Nextcloud इंस्टॉल करने का तरीका जानें। इसमें TLS प्रॉक्सी, डेटा बैकअप और अपग्रेड के लिए सटीक चरण शामिल हैं।

आप वास्तव में क्या बना रहे हैं

यह गाइड एक VPS पर Docker Compose के साथ Nextcloud चलाती है, इसके सामने Let's Encrypt TLS लगाती है, और एक ऐसा बैकअप सेटअप करती है जो वास्तव में रिस्टोर होता है। इसमें चार कंटेनर और एक प्रॉक्सी शामिल हैं: आधिकारिक nextcloud इमेज जो लूपबैक पर लिसन करती है, Postgres जो हर फाइल मेटाडेटा को रखती है, Redis जो फाइल लॉक्स को संभालती है, Nextcloud इमेज की एक दूसरी कॉपी जो केवल क्रॉन लूप चलाती है, और होस्ट पर nginx जो इन सबके सामने TLS टर्मिनेशन करती है। इंस्टॉलेशन में बीस मिनट लगते हैं, और यह वह हिस्सा नहीं है जो मायने रखता है। पहले घंटे में लिए गए दो निर्णय यह तय करते हैं कि क्या एक साल बाद भी आपकी फाइलें सुरक्षित रहेंगी: SQLite के बजाय एक वास्तविक डेटाबेस, और एक ऐसा बैकअप जो डेटा डायरेक्टरी, डेटाबेस और config.php को एक सुसंगत सेट के रूप में कैप्चर करता है।

यह गाइड मानती है कि आपके पास Ubuntu 24.04 LTS या Debian 13 है, Docker का अपना रिपॉजिटरी से इंस्टॉल किया गया Docker Engine और Compose v2 प्लगइन है, और एक DNS A रिकॉर्ड (यदि आपके पास IPv6 है तो AAAA भी) पहले से ही cloud.example.com को VPS की ओर पॉइंट कर रहा है। इसके लिए आपको एक ऐसे सर्वर की आवश्यकता है जिसे आप नियंत्रित करते हैं, क्योंकि किसी और के SaaS पर TLS टर्मिनेशन और डेटाबेस डंप करने का कोई तरीका नहीं है।

Sizing: वास्तव में मेमोरी का उपयोग क्या करता है

Nextcloud की मेमोरी खपत मुख्य रूप से तीन चीजों पर निर्भर करती है, और इनमें से कोई भी स्वयं "Nextcloud" नहीं है।

PHP workers. -apache इमेज प्रत्येक concurrent request को एक वर्कर प्रोसेस से सर्व करती है, जिसमें PHP इंटरप्रेटर होता है। PHP द्वारा रिक्वेस्ट को समाप्त करने से पहले प्रत्येक वर्कर PHP_MEMORY_LIMIT तक बढ़ सकता है। आपकी सबसे खराब स्थिति (worst-case) की रेजिडेंट मेमोरी लगभग concurrent requests × memory limit होती है, और डेस्कटॉप सिंक क्लाइंट प्रति उपयोगकर्ता कई समानांतर कनेक्शन खोलता है। मेमोरी की सीमा उपयोगकर्ता की संख्या नहीं, बल्कि concurrency तय करती है।

डेटाबेस. Postgres प्रत्येक कनेक्शन के लिए एक बैकएंड फोर्क करता है और शेयर्ड बफ़र्स को रेजिडेंट रखता है। इसका वर्किंग सेट बाइट्स की संख्या के बजाय files की संख्या के साथ स्केल होता है: oc_filecache में प्रति उपयोगकर्ता प्रति फ़ाइल एक रो (row) होती है। एक लाख छोटी फ़ाइलें, सौ बड़ी फ़ाइलों की तुलना में डेटाबेस पर अधिक भारी पड़ती हैं।

Preview generation. थंबनेल जनरेट करने के लिए सोर्स इमेज को पूरी रिज़ॉल्यूशन पर मेमोरी में डिकोड किया जाता है। वीडियो प्रीव्यू ffmpeg का उपयोग करते हैं। occ preview:generate-all को चलाने से यह स्पाइक बार-बार होता है, और यह एक छोटे VPS को OOM killer की स्थिति में धकेलने का सबसे सामान्य कारण है।

Redis की तुलनात्मक लागत कम है। बाद में आप जो कुछ भी जोड़ते हैं, जैसे Collabora, full-text search, या antivirus scanner, वे अपने स्वयं के फुटप्रिंट वाली अलग रेजिडेंट सर्विसेज होती हैं, और उन्हें इनेबल करने से पहले आपकी साइजिंग योजना में शामिल होना चाहिए।

यदि आपके पास RAM कम है, तो ये उपाय अपनाएं: PHP_MEMORY_LIMIT को कम करें, preview_max_x / preview_max_y / preview_max_filesize_image को सीमित करें, enabledPreviewProviders को केवल उन फॉर्मेट्स तक सीमित करें जिन्हें आप वास्तव में ब्राउज़ करते हैं, और trashbin_retention_obligation तथा versions_retention_obligation को सेट करें ताकि डेटा डायरेक्टरी चुपचाप आपकी फ़ाइलों के आकार से कई गुना न बढ़ जाए। एक swap file जोड़ें। Swap धीमा होता है, लेकिन अपग्रेड के बीच में OOM kill होना उससे भी बुरा है।

SQLite क्यों विफल होता है

Nextcloud में SQLite का समर्थन शामिल है और इसका आधिकारिक image इसे आसानी से उपयोग कर लेगा। ऐसा न करें। SQLite डेटाबेस-व्यापी लॉक के साथ writes को क्रमबद्ध (serialise) करता है: पूरी फ़ाइल के लिए एक समय में केवल एक ही writer। Nextcloud लगातार लिखता रहता है, जैसे फ़ाइल लॉक, गतिविधि पंक्तियाँ, कैश प्रविष्टियाँ, जॉब स्टेट, और एक डेस्कटॉप क्लाइंट जो डायरेक्टरी ट्री को सिंक करते समय कई समानांतर अनुरोध (parallel requests) भेजता है। इस पैटर्न के तहत आपको SQLSTATE[HY000]: General error: 5 database is locked और HTTP 500 त्रुटियाँ मिलेंगी, और विफलता ठीक उसी समय होती है जब instance उपयोगी होने लगता है।

बाद में रूपांतरण occ db:convert-type के साथ संभव है, लेकिन यह एक लाइव डेटासेट पर एक लंबी, 'सब या कुछ नहीं' (all-or-nothing) वाली माइग्रेशन प्रक्रिया है। शुरुआत से ही Postgres या MariaDB का उपयोग करें।

Compose फ़ाइल

इसे /srv/nextcloud/compose.yaml में रखें, और secrets को एक साथ वाली .env फ़ाइल में 600 मोड के साथ रखें।

services:
  db:
    image: postgres:16-alpine
    restart: unless-stopped
    volumes:
      - db:/var/lib/postgresql/data
    environment:
      POSTGRES_DB: nextcloud
      POSTGRES_USER: nextcloud
      POSTGRES_PASSWORD: ${DB_PASSWORD}

  redis:
    image: redis:7-alpine
    restart: unless-stopped
    command: redis-server --requirepass ${REDIS_PASSWORD}

  app:
    image: nextcloud:31-apache
    restart: unless-stopped
    depends_on: [db, redis]
    ports:
      - "127.0.0.1:8080:80"
    volumes:
      - html:/var/www/html
      - /srv/nextcloud/data:/var/www/html/data
    environment:
      POSTGRES_HOST: db
      POSTGRES_DB: nextcloud
      POSTGRES_USER: nextcloud
      POSTGRES_PASSWORD: ${DB_PASSWORD}
      REDIS_HOST: redis
      REDIS_HOST_PASSWORD: ${REDIS_PASSWORD}
      NEXTCLOUD_ADMIN_USER: admin
      NEXTCLOUD_ADMIN_PASSWORD: ${ADMIN_PASSWORD}
      NEXTCLOUD_TRUSTED_DOMAINS: cloud.example.com
      TRUSTED_PROXIES: 172.16.0.0/12
      OVERWRITEPROTOCOL: https
      OVERWRITECLIURL: https://cloud.example.com
      APACHE_DISABLE_REWRITE_IP: "1"
      PHP_MEMORY_LIMIT: 512M
      PHP_UPLOAD_LIMIT: 10G

  cron:
    image: nextcloud:31-apache
    restart: unless-stopped
    entrypoint: /cron.sh
    depends_on: [db, redis]
    volumes:
      - html:/var/www/html
      - /srv/nextcloud/data:/var/www/html/data

volumes:
  db:
  html:

Major tag को पिन करें और कॉपी करने से पहले Docker Hub पर वर्तमान tag की जाँच करें, अन्यथा 31 का उपयोग न करें। latest भविष्य में किसी docker compose pull अपडेट के दौरान आपको एक major boundary के पार ले जाएगा, और Nextcloud इसका समर्थन नहीं करता है।

Data directory एक bind mount है, named volume नहीं, और यह जानबूझकर किया गया है: एक ऐसा path जिस पर आप सीधे backup tool पॉइंट कर सकें, वह केवल व्यवस्थित होने से कहीं अधिक उपयोगी है। इसे image के www-data UID और Nextcloud द्वारा आवश्यक अनुमतियों (permissions) के साथ बनाएँ:

sudo mkdir -p /srv/nextcloud/data
sudo chown -R 33:33 /srv/nextcloud/data
sudo chmod 0770 /srv/nextcloud/data

Port publish पर ध्यान दें: 127.0.0.1:8080:80। Docker ports को DNAT rules लिखकर publish करता है, जिनका मूल्यांकन ufw की INPUT chain द्वारा packet देखने से पहले ही हो जाता है। एक साधारण 8080:80, ufw की परवाह किए बिना, एक unencrypted Nextcloud को सार्वजनिक इंटरनेट पर डाल देता है। Loopback पर bind करने से यह सार्वजनिक interface से दूर रहता है। इसके बाद firewall को केवल proxy को अनुमति देने की आवश्यकता होती है, और यदि आप SSH को पूरे इंटरनेट के लिए खुला नहीं रखना चाहते हैं, तो self-hosted WireGuard VPN के माध्यम से VPS तक पहुँचना आपको सार्वजनिक नियमों से port 22 को पूरी तरह से हटाने की सुविधा देता है:

sudo ufw allow 22/tcp
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp
sudo ufw enable

इसे docker compose up -d के साथ शुरू करें, फिर docker compose logs -f app पर नज़र रखें। पहली बार boot होने पर पूरी application tree volume में कॉपी हो जाती है और installer चलता है; जब तक यह प्रक्रिया पूरी नहीं हो जाती, container कोई प्रतिक्रिया नहीं देता है।

TLS और reverse proxy

Distro से nginx और certbot इंस्टॉल करें, सही server_name के साथ एक plain port-80 server block बनाएँ, और फिर certbot को इसे rewrite करने दें। HTTP-01 challenge की कार्यप्रणाली, renewal timer और failure modes के बारे में पूरी जानकारी Ubuntu 24.04 पर certbot और nginx के साथ Let's Encrypt certificates जारी करना में दी गई है:

sudo apt install nginx certbot python3-certbot-nginx
sudo certbot --nginx -d cloud.example.com

Certbot ssl_certificate लाइनें और :80:443 redirect जोड़ता है, और एक systemd timer इंस्टॉल करता है जो 90-दिन के certificate को renew करता है। systemctl list-timers | grep certbot के साथ पुष्टि करें कि यह मौजूद है; यदि renewal timer कभी enable नहीं किया गया, तो यह 90-दिन का एक 'fuse' (समय सीमा) बन जाता है।

Proxy block स्वयं:

server {
    listen 443 ssl;
    listen [::]:443 ssl;
    server_name cloud.example.com;

    # certbot manages ssl_certificate / ssl_certificate_key here

    add_header Strict-Transport-Security "max-age=15552000; includeSubDomains" always;

    client_max_body_size 10G;
    client_body_timeout 300s;

    location = /.well-known/carddav { return 301 /remote.php/dav; }
    location = /.well-known/caldav  { return 301 /remote.php/dav; }

    location / {
        proxy_pass http://127.0.0.1:8080;
        proxy_http_version 1.1;
        proxy_set_header Host              $host;
        proxy_set_header X-Real-IP         $remote_addr;
        proxy_set_header X-Forwarded-For   $proxy_add_x_forwarded_for;
        proxy_set_header X-Forwarded-Proto $scheme;
        proxy_set_header X-Forwarded-Host  $host;
        proxy_request_buffering off;
        proxy_buffering off;
        proxy_read_timeout 3600s;
        proxy_send_timeout 3600s;
    }
}

Nginx 1.25 और उसके बाद के वर्ज़न पर, http2 on; जोड़ें। Ubuntu 24.04 में पुराना build है जहाँ इसके समकक्ष listen 443 ssl http2; है। nginx -t आपको बताएगा कि आपका build किसे स्वीकार करता है।

client_max_body_size और लंबे read timeouts ही वे सेटिंग्स हैं जो बड़ी uploads को बीच में ही रुकने से बचाती हैं। proxy_request_buffering off पूरी फाइल को पहले proxy की डिस्क पर spool करने के बजाय upload को सीधे stream करता है।

एक app के लिए host पर nginx का उपयोग करना सबसे सरल और प्रभावी तरीका है। यदि Nextcloud को अन्य containers के साथ VPS साझा करना है, तो कई apps के लिए Docker Compose reverse proxy के रूप में Traefik चलाना routing और certificate issuance को container labels में ले जाता है, और वही client_max_body_size तथा timeout संबंधी चिंताएँ वहाँ middleware और transport settings के रूप में फिर से सामने आती हैं।

trusted_proxies और overwriteprotocol

यहीं पर अधिकांश self-hosted Nextcloud instances में गलती होती है, और इसके लक्षण मूल कारण से असंबंधित लगते हैं।

X-Forwarded-Proto: https का पालन केवल तभी किया जाता है जब अनुरोध trusted_proxies में सूचीबद्ध पते से आता है। जब इसका पालन नहीं किया जाता है, तो Nextcloud यह मानता है कि अनुरोध plain HTTP है और http:// URL जारी करता है; proxy उन्हें HTTPS पर redirect कर देता है; browser उसका अनुसरण करता है; Nextcloud फिर से http:// जारी करता है। यही redirect loop है। OVERWRITEPROTOCOL: https scheme को हर हाल में स्थिर रखता है।

TRUSTED_PROXIES में फँसने का कारण यह है कि जो पता Nextcloud देखता है, वह 127.0.0.1 नहीं है। nginx host पर चलता है और एक published port से जुड़ता है, इसलिए container Docker bridge gateway को देखता है, जो 172.x में कुछ होता है। वास्तविक subnet ढूँढें:

docker network inspect nextcloud_default \
  -f '{{range .IPAM.Config}}{{.Subnet}}{{end}}'

उस CIDR (या कवर करने वाले 172.16.0.0/12) को TRUSTED_PROXIES में डालें। यदि इसे बहुत अधिक विस्तृत सेट करेंगे, तो कोई भी client X-Forwarded-For को spoof कर सकता है; यदि इसे गलत सेट करेंगे, तो हर login gateway पते से आता हुआ दिखाई देगा, brute-force protection एक साथ आपके पूरे instance को block कर देगा, और admin overview में यह संदेश दिखेगा: "The reverse proxy header configuration is incorrect, or you are accessing Nextcloud from a trusted proxy."

OVERWRITECLIURL cron container के लिए महत्वपूर्ण है, जिसके पास hostname का अनुमान लगाने के लिए कोई incoming request नहीं होता है। इसके बिना, background jobs localhost के लिंक उत्पन्न करती हैं और email notifications में अनुपयोगी URL भेजे जाते हैं।

Background jobs: cron, न कि AJAX

Nextcloud का डिफ़ॉल्ट जॉब रनर AJAX है: जॉब्स तब निष्पादित होते हैं जब कोई पेज लोड करता है। रात के 04:00 बजे कोई ब्राउज़िंग नहीं करता, इसलिए ट्रैश एक्सपायरी, वर्ज़न क्लीनअप, प्रीव्यू और फ़ेडरेटेड रिट्राइज़ रुक जाते हैं, और इसका पहला लक्षण यह है कि डेटा डायरेक्टरी का आकार बढ़ना बंद नहीं होता। ऊपर दिया गया cron सर्विस उसी वॉल्यूम पर आधिकारिक /cron.sh लूप चलाता है। Nextcloud को इसके लिए तैयार रहने का निर्देश दें:

docker compose exec -u www-data app php occ background:cron

प्रत्येक occ कमांड इस प्रारूप का पालन करती है: docker compose exec -u www-data app php occ <command>। इसे एलियास (alias) बनाना उपयोगी रहता है।

Backups: तीन चीजें, या कुछ भी नहीं

केवल filesystem का backup लेने पर एक broken instance ही restore हो पाता है। data directory में bytes होते हैं; Postgres में file cache, shares, users और app state होता है; config.php में database credentials, instance ID और password salt होते हैं। database के बिना files restore करने पर Nextcloud उन्हें देख नहीं पाएगा। config.php के बिना database restore करने पर वह database को open नहीं कर पाएगा। एक पुराने database को नई data directory के साथ restore करने पर shares उन files की ओर इशारा करेंगे जो अपनी जगह बदल चुकी हैं।

एक quiesced instance से इन तीनों का backup लें:

#!/usr/bin/env bash
set -euo pipefail
cd /srv/nextcloud
DEST="/var/backups/nextcloud/$(date -u +%Y%m%dT%H%M%SZ)"
mkdir -p "$DEST"

occ() { docker compose exec -T -u www-data app php occ "$@"; }

occ maintenance:mode --on
trap 'occ maintenance:mode --off' EXIT

docker compose exec -T db \
  pg_dump -U nextcloud --clean --if-exists nextcloud | gzip > "$DEST/db.sql.gz"

docker compose exec -T app \
  tar -C /var/www/html -cf - config custom_apps themes > "$DEST/app.tar"

rsync -a --delete /srv/nextcloud/data/ /var/backups/nextcloud/data/

Maintenance mode ही वह स्थिति है जिससे dump और file copy एक-दूसरे के साथ मेल खाते हैं। यदि आप इसे छोड़ देते हैं, तो अंततः आप ऐसा database capture कर लेंगे जो ऐसी file को reference करता है जहाँ तक rsync अभी पहुँचा ही नहीं था। ध्यान दें कि script timestamped database dumps को रखती है, लेकिन data directory का केवल एक rolling mirror ही रखती है, rsync --delete हर बार इसे overwrite कर देता है, इसलिए केवल सबसे नया dump ही file copy के साथ मेल खाता है।

इसके बाद इसे server से बाहर निकालें। जो backup उसी VPS पर रहता है जिसका वह backup है, वह केवल एक copy है, backup नहीं। object storage या किसी दूसरे host के विरुद्ध restic का उपयोग करना सामान्य समाधान है, और इसकी deduplication क्षमता nightly tarball की तुलना में data directory को कहीं बेहतर तरीके से संभालती है। repository init से लेकर nightly timer और restore drill तक का पूरा setup off-box VPS backups with restic में दिया गया है।

Restore करना केवल backup का उल्टा क्रम नहीं है। एक नया start किया गया stack installer को चलाता है और एक बिल्कुल नया config.php, एक नई instance ID और password salt लिखता है, और उस नई identity के ऊपर dump को import करने से sessions और share tokens टूट जाते हैं। पहले पुरानी identity को वापस लाएं, इस क्रम में:

docker compose up -d && docker compose stop app cron    # create the volumes, then halt the app
sudo rsync -a --delete /var/backups/nextcloud/data/ /srv/nextcloud/data/
docker compose run --rm -T --entrypoint "" app \
  tar -C /var/www/html -xf - < app.tar                  # the original config.php returns
gunzip -c db.sql.gz | docker compose exec -T db psql -U nextcloud -d nextcloud
docker compose start app cron
docker compose exec -T -u www-data app php occ maintenance:mode --off
docker compose exec -T -u www-data app php occ files:scan --all

files:scan file cache का disk पर मौजूद वास्तविक data के साथ मिलान करता है। इसकी एक बार किसी spare VPS पर अभ्यास (rehearse) जरूर करें, इससे पहले कि आपको इसकी वास्तविक आवश्यकता पड़े। disk पर मौजूद bytes और Postgres में मौजूद metadata के बीच का यही विभाजन इस तरह के हर दूसरे app पर लागू होता है, यही कारण है कि an Immich backup that captures the library but not the database restores to an empty timeline होता है।

Upgrades: एक बार में एक major version

Nextcloud एक बार में केवल एक major version के upgrade का समर्थन करता है। 29 से सीधे 31 पर जाने पर यह सही ढंग से काम नहीं करता, बल्कि Exception: Updates between multiple major versions and downgrades are unsupported. के साथ विफल हो जाता है और आपको maintenance mode में छोड़ देता है।

Docker upgrade की प्रक्रिया यह है: backup लें, app और cron दोनों services में tag को 31 से बदलकर 32 करें, फिर docker compose pull && docker compose up -d चलाएं, और उसके बाद docker compose logs -f app करें। Image का entrypoint मौजूदा डेटा के मुकाबले नए code का पता लगाता है और स्वयं occ upgrade चलाता है। इसे बीच में न रोकें। जब logs शांत हो जाएं, तो docker compose exec -u www-data app php occ status चलाएं और versionstring की जांच करें कि क्या apps वापस enabled हो गए हैं।

दो नियम जो आपको बचाएंगे: एक major version बढ़ाएं, पुष्टि करें, फिर अगला बढ़ाएं। और app service पर tag को कभी भी cron को बदले बिना न बदलें; एक ही database पर दो अलग-अलग Nextcloud versions का उपयोग करना data corruption का कारण बनता है।

वे त्रुटियाँ जो आपको वास्तव में दिखाई देंगी

"Your data directory is readable by other users. Please change the permissions to 0770." bind-mounted डायरेक्टरी में group या world read बिट्स सेट हैं। sudo chmod 0770 /srv/nextcloud/data और sudo chown -R 33:33 /srv/nextcloud/data देखें।

"Your data directory is invalid. Ensure there is a file called .ocdata in the root." bind mount ऐसी जगह पॉइंट कर रहा है जहाँ Nextcloud कभी इनिशियलाइज़ नहीं हुआ, पाथ में टाइपिंग की गलती है, या किसी वर्किंग इंस्टेंस के नीचे एक नई खाली डायरेक्टरी आ गई है। पुष्टि करें कि होस्ट पाथ वॉल्यूम लाइन से मेल खाता है।

"Access through untrusted domain." रिक्वेस्ट में मौजूद hostname trusted_domains में नहीं है। NEXTCLOUD_TRUSTED_DOMAINS केवल पहली बार इंस्टाल करते समय लागू होता है; बाद में इसे लाइव सेट करें: occ config:system:set trusted_domains 1 --value=cloud.example.com

502 Bad Gateway, साथ में /var/log/nginx/error.log में connect() failed (111: Connection refused) while connecting to upstream। nginx 127.0.0.1:8080 पर किसी चीज़ तक नहीं पहुँच सका। या तो कंटेनर अभी भी इनिशियलाइज़ हो रहा है (docker compose logs app चेक करें), यह एग्जिट हो गया है (docker compose ps), या पब्लिश लाइन proxy_pass पोर्ट से मेल नहीं खाती। ss -ltnp | grep 8080 के साथ पुष्टि करें।

एक रीडायरेक्ट लूप, या एडमिन ओवरव्यू में "insecure" चेतावनियाँ। OVERWRITEPROTOCOL: https गायब है, या TRUSTED_PROXIES में Docker गेटवे सबनेट शामिल नहीं है। ऊपर दिया गया प्रॉक्सी सेक्शन देखें।

LockedException: "files/..." is locked REDIS_HOST सेट होने पर, इमेज Redis को लॉकिंग बैकएंड के रूप में कॉन्फ़िगर करती है और पुराने लॉक्स दुर्लभ होते हैं। इसके बिना, लॉक्स डेटाबेस टेबल oc_file_locks में रहते हैं और राइटिंग के बीच में कोई रिक्वेस्ट किल होने पर पंक्तियाँ (rows) पीछे छूट जाती हैं। मैन्युअल रूप से लॉक पंक्तियों को हटाने से पहले पुष्टि करें कि Redis वास्तव में उपयोग में है, occ config:system:get memcache.locking को Redis क्लास रिटर्न करनी चाहिए।

"The PHP memory limit is below the recommended value of 512MB." PHP_MEMORY_LIMIT को बढ़ाएं और कंटेनर को फिर से बनाएँ। याद रखें कि यह आपके वर्स्ट-केस सीलिंग (worst-case ceiling) को कैसे प्रभावित करता है।

स्केल बढ़ने पर क्या समस्याएं आती हैं

पहली बाधा डेटा डायरेक्टरी का वॉल्यूम से बड़ा हो जाना है। VPS पर वॉल्यूम बढ़ाना एक resize और फिर filesystem को बड़ा करने की प्रक्रिया है। इसे 100% भर जाने के बाद करने के बजाय पहले से शेड्यूल करना बहुत कम कष्टदायक होता है। डिस्क उपयोग पर अभी अलर्ट सेट करें, बाद के लिए न छोड़ें।

दूसरी बाधा oc_filecache है। रो (row) की संख्या बढ़ने के साथ फाइल लिस्टिंग और सिंक स्कैन धीमे हो जाते हैं। इसका समाधान डेटाबेस का काम है: Postgres को तेज स्टोरेज पर रखें, इसे पर्याप्त shared memory का उपयोग करने दें, और कचरे व पुराने वर्ज़न्स को हमेशा जमा होने देने के बजाय retention सेटिंग्स के साथ हटाते रहें।

तीसरी बाधा प्रीव्यू जनरेशन है जो बाकी सभी चीजों के साथ प्रतिस्पर्धा करती है। एक छोटे बॉक्स पर, प्रीव्यू प्रोवाइडर्स को सीमित रखें और काम के घंटों के दौरान कभी भी occ preview:generate-all न चलाएं। यदि आप मुख्य रूप से फोन कैमरा रोल स्टोर कर रहे हैं, तो थंबनेल बनाने का काम एक अलग फोटो सर्वर पर होना चाहिए। RAM, फोन ऐप्स और बैकअप कमांड्स पर PhotoPrism और Immich की तुलना में बताया गया है कि Nextcloud बॉक्स की तुलना में इनकी लागत क्या है।

इसके अलावा, सच यह है कि अतिरिक्त सेवाओं को अपनी अलग मशीन की आवश्यकता होती है। Collabora और full-text search अलग-अलग रेजिडेंट सर्विसेज हैं जिनकी अपनी मेमोरी प्रोफाइल होती है। इन्हें उसी बॉक्स पर रखना जहाँ आपकी फाइलों की एकमात्र कॉपी मौजूद है, बिना किसी लाभ के विफलता के दायरे (failure domain) को बढ़ा देता है। यदि इन-ब्राउज़र डॉक्यूमेंट एडिटिंग वह अतिरिक्त सुविधा है जो आप चाहते हैं, तो OnlyOffice और Collabora को अलग करने वाली वेंडर RAM सीमाएं और कनेक्शन लिमिट्स यह तय करती हैं कि 2 से 4 GB का VPS किसे संभाल सकता है। जब वॉल्यूम का आकार सही न रहे, तो फाइल स्टोरेज को S3-compatible प्राइमरी स्टोरेज पर ले जाएं। ध्यान दें कि इससे बैकअप आसान होने के बजाय कठिन हो जाता है: डेटाबेस में अभी भी मेटाडेटा होता है, और इसे बकेट के साथ तालमेल बिठाकर डंप किया जाना चाहिए।

एक बार जब इंस्टेंस वास्तविक उपयोगकर्ताओं को सेवा देने लगे, तो इसके सामने Uptime Kuma लगाएं ताकि सिंक क्लाइंट्स को पता चलने से पहले आपको डाउनटाइम की जानकारी मिल जाए। एक प्राइवेट क्लाउड आपके अपने मेल सर्वर के साथ अच्छी तरह काम करता है। यदि आप सेवाओं को मैन्युअल रूप से जोड़ना नहीं चाहते हैं, तो Cloudron, CasaOS और Coolify उन प्लेटफॉर्म्स की तुलना करते हैं जो यह काम आपके लिए करते हैं। यदि उस सूची में अगला नंबर एक सेल्फ-होस्टेड सर्च इंजन का है, तो ऊपर बताई गई समस्याओं से अलग तरह की समस्याओं की अपेक्षा करें: SearXNG की 429 एरर्स या तो इसके अपने रेट लिमिटर से आती हैं या अपस्ट्रीम इंजन द्वारा आपके VPS IP को ब्लॉक करने से, और केवल लॉग ही आपको बता सकता है कि समस्या क्या है।

FAQ

क्या मैं Postgres के बजाय SQLite पर Nextcloud चला सकता हूँ?

आप ऐसा कर सकते हैं और official image आपको इसकी अनुमति भी देती है, लेकिन एक single desktop sync client द्वारा समानांतर requests भेजने पर SQLSTATE[HY000]: General error: 5 database is locked और HTTP 500 errors आने लगेंगे। SQLite पूरे database पर write lock लगा देता है, जबकि Nextcloud लगातार data लिखता है, file locks बनाता है, activity rows अपडेट करता है और job state बदलता है। शुरुआत Postgres या MariaDB के साथ करें; occ db:convert-type मौजूद है, लेकिन यह live data पर एक लंबी और जोखिम भरी migration प्रक्रिया है।

Nextcloud VPS को वास्तव में कितनी RAM की आवश्यकता होती है?

संसाधनों का आकलन user की संख्या के बजाय concurrency (एक साथ काम करने वाले users) के आधार पर करें। सबसे खराब स्थिति में resident memory लगभग concurrent requests की संख्या को PHP_MEMORY_LIMIT से गुणा करने पर प्राप्त होती है, जिसमें Postgres shared buffers, प्रति connection एक backend और preview generation के दौरान होने वाली spikes को जोड़ना होता है। यदि आप previews को सीमित कर दें और swap का उपयोग करें, तो 2 GB का server एक छोटे परिवार के लिए पर्याप्त है; यदि आप Collabora या full-text search जोड़ते हैं, तो आपको अतिरिक्त resident services के लिए अलग से संसाधन आवंटित करने होंगे।

nginx reverse proxy के पीछे बड़ी uploads क्यों विफल हो जाती हैं?

इसके लिए आमतौर पर proxy की दो settings जिम्मेदार होती हैं: client_max_body_size को 1 MB के default मान पर छोड़ने से request बीच में ही कट जाती है, और कम proxy_read_timeout / proxy_send_timeout मान लंबी transfers को बीच में ही रोक देते हैं। दोनों मानों को पर्याप्त रूप से बढ़ाएं, proxy_request_buffering off को spool के बजाय stream पर सेट करें, और app container पर PHP_UPLOAD_LIMIT को भी उसी के अनुसार बढ़ाएं।

Nextcloud redirect loop में क्यों फंस जाता है या reverse proxy के बारे में चेतावनी क्यों देता है?

Container को 127.0.0.1 पर nginx दिखाई नहीं देता, उसे केवल Docker bridge gateway दिखाई देता है, जो 172.x में कहीं स्थित होता है। जब यह address TRUSTED_PROXIES में मौजूद नहीं होता, तो X-Forwarded-Proto: https header को अनदेखा कर दिया जाता है, Nextcloud http:// URLs जारी करता है, और proxy उन्हें वापस bounce कर देता है। TRUSTED_PROXIES को वास्तविक bridge subnet पर सेट करें और OVERWRITEPROTOCOL: https को pin करें।

क्या मैं Nextcloud को सीधे 29 से 31 पर upgrade कर सकता हूँ?

नहीं। Nextcloud प्रति upgrade केवल एक major version का समर्थन करता है, और version छोड़ने पर प्रक्रिया Updates between multiple major versions and downgrades are unsupported. के साथ रुक जाएगी, जिससे instance maintenance mode में फंस जाएगा। Backup लें, app और cron दोनों services पर tag को एक major version बढ़ाएं, docker compose pull && docker compose up -d चलाएं, occ status के साथ पुष्टि करें, और फिर यही प्रक्रिया दोहराएं।