Ubuntu 24.04-এ MinIO সেটআপ করার নিয়ম
Ubuntu 24.04 VPS-এ MinIO ইনস্টল করার পূর্ণাঙ্গ গাইড। এখানে ভেরিফাইড বাইনারি সেটআপ, systemd ইউনিট কনফিগারেশন, mc কমান্ডের ব্যবহার এবং restic ব্যাকআপ টার্গেট তৈরির পদ্ধতি দেখানো হয়েছে।
MinIO-এর মাধ্যমে সেলফ-হোস্টেড অবজেক্ট স্টোরেজ আপনাকে যা দেয়
MinIO হলো একটি সেলফ-হোস্টেড অবজেক্ট স্টোরেজ যা Amazon S3 API সমর্থন করে। আপনি restic বা যেকোনো S3 SDK-কে আপনার নিজস্ব সার্ভারের দিকে নির্দেশ করুন, একটি এন্ডপয়েন্ট সেটিং পরিবর্তন করুন, এবং ক্লায়েন্ট কোনো পার্থক্য বুঝতে পারবে না। এই নির্দেশিকাটি Ubuntu 24.04-এ একটি সিঙ্গেল নোড তৈরি করে: একটি ভেরিফাইড বাইনারি, একটি ডেডিকেটেড সিস্টেম ইউজার, একটি systemd ইউনিট যা root ক্রেডেনশিয়ালগুলোকে ইউনিট ফাইলের বাইরে রাখে এবং একটি বাকেট যেখানে restic ব্যাকআপ রাখে।
S3 (simple storage service) হলো একটি HTTP API, কোনো ফাইলসিস্টেম নয়। আপনি একটি বাকেটে একটি কী-এর অধীনে একটি অবজেক্ট PUT করেন এবং সেটি GET করে ফেরত পান, এখানে কোনো পার্শিয়াল রাইট বা রিনেমের সুযোগ নেই। ব্যাকআপ টুলগুলো এই মডেলটি পছন্দ করে, কারণ একটি অবজেক্ট হয় সম্পূর্ণভাবে পৌঁছায় অথবা মোটেও পৌঁছায় না।
একটি নোড আপনার ডেটার একটি কপি ধারণ করে। এটিই সেই বিনিময় যা আপনি করছেন। আপনি একটি VPS-এর খরচে আপনার নিয়ন্ত্রণাধীন একটি S3 এন্ডপয়েন্ট পাচ্ছেন, এবং সেই সাথে ক্লাউড প্রোভাইডার আগে যে কাজগুলো করতো, যেমন নষ্ট হয়ে যাওয়া ডিস্ক প্রতিস্থাপন করা থেকে শুরু করে সার্ভার সফটওয়্যার প্যাচ করা পর্যন্ত, তার সব দায়িত্ব এখন আপনার। শেষের দিকের সেকশনে স্পষ্টভাবে বলা হয়েছে কখন এই বিনিময়টি লাভজনক।
জুলাই 2026-এ MinIO কমিউনিটি এডিশনের অবস্থা
এই অংশে কাজ শুরু করার আগে এটি পড়ে নিন, কারণ সম্প্রতি এতে পরিবর্তন আনা হয়েছে। মে 2025-এ MinIO তাদের কমিউনিটি এডিশনের ওয়েব কনসোল থেকে অ্যাডমিনিস্ট্রেশন ফিচারগুলো সরিয়ে ফেলেছে। ব্রাউজারে এখন কেবল একটি অবজেক্ট ব্রাউজার অবশিষ্ট আছে, তাই বাকেট (buckets) এবং অ্যাক্সেস কি (access keys) এখন mc কমান্ড লাইন ক্লায়েন্টের মাধ্যমে পরিচালনা করতে হয়।
2025 সালের পরবর্তী সময়ে MinIO প্রি-কম্পাইল করা কমিউনিটি বাইনারি প্রকাশ করা বন্ধ করে দিয়েছে। প্রজেক্টের README এখন বলছে যে কমিউনিটি এডিশন শুধুমাত্র সোর্স কোড হিসেবে বিতরণ করা হয়। পুরনো ডাউনলোড ইউআরএলগুলো এখনও কাজ করছে: জুলাই 2026 পর্যন্ত সেগুলো সার্ভার বিল্ড RELEASE.2025-09-07T16-13-09Z এবং ক্লায়েন্ট বিল্ড RELEASE.2025-08-13T08-35-41Z প্রদান করছে, এবং এর পরে নতুন কোনো কমিউনিটি বিল্ড প্রকাশিত হয়নি। সুতরাং, নিচের বাইনারিটি আসল এবং এটি কার্যকর, তবে এটি এখন অপরিবর্তনীয় (frozen)। সেপ্টেম্বর 2025-এর পরে প্রকাশিত কোনো নিরাপত্তা আপডেট এতে অন্তর্ভুক্ত নেই।
এই একটি তথ্যই এই গাইডের বাকি অংশকে প্রভাবিত করে। এই কারণেই এখানে MinIO 127.0.0.1 পোর্টে লিসেন করে এবং শুধুমাত্র আপনার নিয়ন্ত্রিত একটি প্রক্সির মাধ্যমে ইন্টারনেটে সংযুক্ত হয়। আপনি যদি সিকিউরিটি আপডেটগুলো পেতে চান, তবে সোর্স থেকে বিল্ড করুন। ভেন্ডর README একটি একক কমান্ড, go install github.com/minio/minio@latest প্রদান করে, যার জন্য একটি Go টুলচেইন প্রয়োজন এবং এটি বাইনারিটিকে ~/go/bin/minio-এ রাইট করে। সেই বাইনারিটিকে /usr/local/bin/minio-এ ইনস্টল করুন এবং এর পরের প্রতিটি ধাপ অপরিবর্তিত থাকবে।
MinIO বাইনারি ইনস্টল করুন এবং ডাউনলোড যাচাই করুন
পিন করা রিলিজ এবং এর প্রকাশিত চেকসাম ডাউনলোড করুন। -f ফ্ল্যাগটি ব্যবহার করলে HTTP ত্রুটির ক্ষেত্রে curl ব্যর্থ হয়, পরিবর্তে এটি আপনার দেওয়া নামে ত্রুটিপূর্ণ পেজটি সেভ করে না। এটি গুরুত্বপূর্ণ কারণ অন্যথায় ব্যবহারকারীরা ভুলবশত একটি 404 পেজ ইনস্টল করে ফেলেন এবং কেন এটি এক্সিকিউট হচ্ছে না তা বুঝতে পারেন না।
cd /tmp
REL=RELEASE.2025-09-07T16-13-09Z
curl -fsSL "https://dl.min.io/server/minio/release/linux-amd64/archive/minio.$REL" -o minio
curl -fsSL "https://dl.min.io/server/minio/release/linux-amd64/archive/minio.$REL.sha256sum" -o minio.sha256sumদুটি হ্যাশ তুলনা করুন, এবং শুধুমাত্র হ্যাশগুলোই তুলনা করুন।
published=$(awk '{print $1}' minio.sha256sum)
downloaded=$(sha256sum minio | awk '{print $1}')
[ "$published" = "$downloaded" ] && echo "checksum ok"এখানে sha256sum -c minio.sha256sum ব্যবহার করবেন না। সেই ফাইলের ভেতরে হ্যাশের পরে লেখা লেবেলটি হলো minio.RELEASE.2025-09-07T16-13-09Z, এবং আমরা ডাউনলোডটিকে minio নামে সেভ করেছি, তাই -c এমন একটি ফাইলের খোঁজ করে যা বিদ্যমান নেই। এটি No such file or directory রিপোর্ট করে এবং তারপর WARNING: 1 listed file could not be read দেখায়, যা দেখে মনে হতে পারে ডাউনলোডটি করাপ্টেড হয়েছে, কিন্তু আসলে তা নয়। লেবেলটি কেবল একটি নাম। হ্যাশ হলো সেই অংশ যা নিশ্চয়তা প্রদান করে।
এই চেকটি কী প্রমাণ করে সে সম্পর্কে পরিষ্কার ধারণা রাখুন। বাইনারি এবং হ্যাশ একই ভেন্ডরের কাছ থেকে একই কানেকশনের মাধ্যমে আসে, তাই একটি মিল প্রমাণ করে যে ডাউনলোডটি সম্পূর্ণ হয়েছে এবং ট্রানজিটের সময় ক্ষতিগ্রস্ত বা পরিবর্তিত হয়নি। এটি প্রমাণ করে না যে ভেন্ডর বিশ্বাসযোগ্য। এটি একটি ভিন্ন সমস্যা এবং কোনো sha256sum কমান্ড এটি সমাধান করতে পারে না।
sudo install -o root -g root -m 755 minio /usr/local/bin/minio
minio --versionminio --version কমান্ডটি minio version RELEASE.2025-09-07T16-13-09Z এবং তার সাথে কিছু বিল্ড লাইন প্রিন্ট করে। এখানে Permission denied আসার অর্থ হলো মোডটি ভুল, এবং command not found আসার অর্থ হলো /usr/local/bin আপনার PATH-এ নেই।
একটি সিস্টেম ইউজার এবং ডেটা ডিরেক্টরি তৈরি করুন
MinIO নেটওয়ার্ক থেকে আপলোড গ্রহণ করে, তাই এটি root হিসেবে চালানো উচিত নয়। এটিকে এমন একটি অ্যাকাউন্ট দিন যার কোনো হোম ডিরেক্টরি নেই এবং কোনো লগইন শেল নেই।
sudo groupadd -r minio-user
sudo useradd -M -r -g minio-user -s /usr/sbin/nologin minio-user
sudo mkdir -p /var/lib/minio/data
sudo chown -R minio-user:minio-user /var/lib/minio
sudo chmod 750 /var/lib/minio-r 1000-এর নিচে UID সহ একটি সিস্টেম অ্যাকাউন্ট তৈরি করে, যা এটিকে সাধারণ ব্যবহারকারীদের পরিসরের বাইরে রাখে। -M হোম ডিরেক্টরি তৈরি করা এড়িয়ে যায়, কারণ যে অ্যাকাউন্টে কখনোই লগইন করা হয় না, তার সেখানে কিছু রাখার প্রয়োজন নেই। id minio-user দিয়ে ফলাফলটি যাচাই করুন এবং stat -c '%U %a' /var/lib/minio দিয়ে দেখুন, যা minio-user 750 প্রিন্ট করবে।
ডেটা ডিরেক্টরিটিতে শুধুমাত্র রিড করার ক্ষমতাই নয়, সেই ইউজারের রাইট করার ক্ষমতাও থাকতে হবে। প্রথমবার চালু হওয়ার সময় MinIO তার নিজস্ব কনফিগারেশন রাখার জন্য ভলিউমের ভেতরে একটি .minio.sys ডিরেক্টরি তৈরি করে, তাই root-এর মালিকানাধীন ডিরেক্টরি থাকলে MinIO স্টার্টআপের সময় বন্ধ হয়ে যায় এবং একটি মেসেজ দেখায় যা permission denied দিয়ে শেষ হয়। আপনি এই পদ্ধতিতে যে সার্ভিসই চালান না কেন, একই নিয়ম প্রযোজ্য এবং VPS-এ লিস্ট-প্রিভিলেজ সার্ভিস ইউজার বিষয়টি বিস্তারিত আলোচনা করে।
রুট ক্রেডেনশিয়ালগুলো একটি এনভায়রনমেন্ট ফাইলে রাখুন
রুট ক্রেডেনশিয়ালগুলো প্রতিটি বাকেটের অ্যাক্সেস প্রদান করে, তাই এগুলো ইউনিট ফাইলে রাখা উচিত নয়, কারণ ইউনিট ফাইলটি যে কেউ পড়তে পারে। প্রথমে সঠিক মোড ব্যবহার করে ফাইলটি তৈরি করুন এবং তারপর তাতে তথ্য লিখুন, যাতে পাসওয়ার্ডটি কোনো মুহূর্তের জন্যও এমন কোনো ফাইলে না থাকে যা অন্য কেউ পড়তে পারে।
sudo install -o root -g root -m 600 /dev/null /etc/default/minio
printf 'MINIO_ROOT_USER=minio-root\nMINIO_ROOT_PASSWORD=%s\nMINIO_VOLUMES="/var/lib/minio/data"\nMINIO_OPTS="--address 127.0.0.1:9000 --console-address 127.0.0.1:9001"\n' "$(openssl rand -base64 24)" | sudo tee /etc/default/minio > /dev/null
sudo sed -n 's/^MINIO_ROOT_PASSWORD=//p' /etc/default/miniotee বিদ্যমান ফাইলকে নতুন করে তৈরি না করে সেটিকে ট্রাঙ্কেট (truncate) করে, ফলে ফাইলের মোড 600 এবং মালিকানা root হিসেবেই বজায় থাকে। এটি ইচ্ছাকৃতভাবেই করা হয়েছে। systemd ফাইলটিকে EnvironmentFile হিসেবে পড়ে, এরপর এটি প্রিভিলেজ কমিয়ে User=-এ নিয়ে আসে। এর অর্থ হলো, সার্ভিস অ্যাকাউন্টটির নিজের ক্রেডেনশিয়াল পড়ার প্রয়োজন হয় না। সার্ভিসটি চালু হওয়ার পর, sudo -u minio-user cat /etc/default/minio কমান্ড দিয়ে তা যাচাই করুন। এই কমান্ডটি অবশ্যই Permission denied আউটপুট প্রদর্শন করবে।
সার্ভিসটি শুরু করার আগে MinIO-এর দুটি আচরণ জেনে রাখা প্রয়োজন। কোনো MINIO_ROOT_USER এবং MINIO_ROOT_PASSWORD এনভায়রনমেন্টে না থাকলে, MinIO চালু হতে অস্বীকার করে না। এটি ডকুমেন্টেশনে উল্লিখিত ডিফল্ট ক্রেডেনশিয়াল minioadmin:minioadmin দিয়ে চালু হয়, যা যেকোনো স্ক্যানার সবার আগে চেষ্টা করে এবং এটি দেখতে সম্পূর্ণ স্বাভাবিক মনে হয়। 8 অক্ষরের কম পাসওয়ার্ড হলে MinIO তা প্রত্যাখ্যান করে: স্টার্টআপের সময় MinIO একটি ত্রুটি বার্তা দিয়ে বন্ধ হয়ে যায়, কারণ অ্যাক্সেস কি-এর জন্য কমপক্ষে 3টি এবং সিক্রেট কি-এর জন্য কমপক্ষে 8টি অক্ষর প্রয়োজন।
MINIO_VOLUMES হলো ডেটা পাথ এবং MINIO_OPTS-এ ফ্ল্যাগগুলো থাকে। 127.0.0.1-এ বাইন্ড করার অর্থ হলো, এই VPS-এর বাইরের কেউ এখনও S3 API-তে পৌঁছাতে পারবে না, যা একটি সঠিক ডিফল্ট সেটিংস। পরবর্তীতে একটি প্রক্সির মাধ্যমে সার্টিফিকেট ব্যবহার করে আপনি ইচ্ছাকৃতভাবে এটি উন্মুক্ত করবেন।
systemd ইউনিট তৈরি করুন
/etc/systemd/system/minio.service তৈরি করুন:
[Unit]
Description=MinIO object storage
Documentation=https://github.com/minio/minio
Wants=network-online.target
After=network-online.target
[Service]
User=minio-user
Group=minio-user
EnvironmentFile=/etc/default/minio
ExecStart=/usr/local/bin/minio server $MINIO_VOLUMES $MINIO_OPTS
Restart=always
RestartSec=5
LimitNOFILE=65536
NoNewPrivileges=true
[Install]
WantedBy=multi-user.targetEnvironmentFile-এ কোনো অগ্রবর্তী - নেই, এবং এটি কোনো ভুল নয় বরং একটি সচেতন সিদ্ধান্ত। ড্যাশ চিহ্নটি থাকলে, systemd কোনো ফাইল খুঁজে না পেলে তা উপেক্ষা করে এবং MinIO চালু করে দেয়, যার ফলে ফাইল মুছে গেলে বা পাথের বানান ভুল থাকলে সার্ভারটি নীরবে minioadmin:minioadmin-এ চলতে থাকে। ড্যাশ না থাকলে, কোনো ফাইল অনুপস্থিত থাকলে MinIO চালু হওয়ার আগেই ইউনিটটি ব্যর্থ হয় এবং journalctl -u minio-এ Failed to load environment files: No such file or directory প্রদর্শিত হয়। সার্ভার নীরবে ডিফল্ট পাসওয়ার্ড গ্রহণ করার চেয়ে একটি ইউনিট চালু হতে অস্বীকার করলে তা শনাক্ত করা অনেক সহজ।
$MINIO_VOLUMES এবং $MINIO_OPTS ইচ্ছাকৃতভাবে উদ্ধৃতি চিহ্ন (quote) ছাড়া রাখা হয়েছে, কারণ systemd উদ্ধৃতিহীন ভেরিয়েবলগুলোকে হোয়াইটস্পেস অনুযায়ী আলাদা আলাদা আর্গুমেন্টে বিভক্ত করে। এভাবেই MINIO_OPTS-এর চারটি শব্দ minio server-এর চারটি আর্গুমেন্টে পরিণত হয়। LimitNOFILE=65536 ফাইল ডেসক্রিপটর লিমিট বৃদ্ধি করে, কারণ প্রতিটি খোলা সংযোগ এবং প্রতিটি খোলা ডেটা ফাইলের জন্য একটি করে ডেসক্রিপটর প্রয়োজন হয় এবং লোড বাড়লে ডিফল্ট 1024 লিমিট দ্রুত শেষ হয়ে যায়।
sudo systemctl daemon-reload
sudo systemctl enable --now minio
systemctl is-active minio
curl -fsS -o /dev/null -w '%{http_code}\n' http://127.0.0.1:9000/minio/health/liveis-active-এর আউটপুট active হওয়া উচিত এবং হেলথ এন্ডপয়েন্ট থেকে 200 উত্তর আসা উচিত। journalctl -u minio -n 20 --no-pager কমান্ডটি সেই API অ্যাড্রেস দেখায় যেখানে সার্ভারটি লিসেন করছে। যদি ইউনিটটি বারবার রিস্টার্ট হতে থাকে, তবে systemd হাল ছেড়ে দেয় এবং Start request repeated too quickly লগ করে, যার অর্থ হলো MinIO প্রতিটি প্রচেষ্টাতেই বন্ধ হয়ে যাচ্ছে: এর কারণ ওই বার্তার উপরের লাইনগুলোতে লেখা থাকে, তাই উপরের দিকে পড়ুন।
আরও বেশি আইসোলেশনের জন্য, [Service] সেকশনে ProtectSystem=full এবং ProtectHome=true যোগ করুন। উভয়টির জন্যই হোস্ট কার্নেল থেকে মাউন্ট নেমস্পেস প্রয়োজন। OpenVZ বা LXC-এর মতো কন্টেইনার ভার্চুয়ালাইজেশন, যা হোস্ট কার্নেল শেয়ার করে, সেখানে এগুলো ব্যর্থ হতে পারে এবং তখন ইউনিটটি status=226/NAMESPACE রিপোর্ট করে। এই দুটি লাইন মুছে ফেললে এটি চালু হবে। ইউনিটটি একটি সাধারণ ইউনিট এবং VPS-এ systemd সার্ভিস এবং টাইমার বাকি ডিরেক্টিভগুলো নিয়ে আলোচনা করে।
mc ইনস্টল করা এবং একটি রাউন্ড ট্রিপ যাচাই করা
MinIO ক্লায়েন্ট হলো mc। এটিকে apt install mc দিয়ে ইনস্টল করবেন না। সেই প্যাকেজটি হলো Midnight Commander, যা একটি ফাইল ম্যানেজার এবং MinIO-এর সাথে এর কোনো সম্পর্ক নেই।
cd /tmp
curl -fsSL https://dl.min.io/client/mc/release/linux-amd64/mc -o mc
curl -fsSL https://dl.min.io/client/mc/release/linux-amd64/mc.sha256sum -o mc.sha256sum
[ "$(awk '{print $1}' mc.sha256sum)" = "$(sha256sum mc | awk '{print $1}')" ] && echo "checksum ok"
sudo install -o root -g root -m 755 mc /usr/local/bin/mcসার্ভারটিকে একটি অ্যালিয়াস (alias) হিসেবে রেজিস্টার করুন, তারপর এর মাধ্যমে একটি অবজেক্ট স্থানান্তর করুন।
MINIO_PASS=$(sudo sed -n 's/^MINIO_ROOT_PASSWORD=//p' /etc/default/minio)
mc alias set local http://127.0.0.1:9000 minio-root "$MINIO_PASS"
mc mb local/backups
echo "hello object storage" > /tmp/hello.txt
mc cp /tmp/hello.txt local/backups/hello.txt
mc ls local/backups
mc cat local/backups/hello.txtmc ls কমান্ডটি hello.txt-কে তার আকারসহ তালিকাভুক্ত করবে এবং mc cat কমান্ডটি hello object storage প্রিন্ট করবে। এই রাউন্ড ট্রিপটিই সার্ভারটি কাজ করার প্রকৃত প্রমাণ, কারণ এটি সেই একই সাইন করা S3 রিকোয়েস্টগুলো তৈরি করে যা অন্য যেকোনো ক্লায়েন্ট করবে। আপনি যদি দ্বিতীয় কোনো মতামত চান, তবে mc admin info local সার্ভারের স্ট্যাটাস প্রিন্ট করে দেখাবে।
এখন সার্ভারটি খালি থাকা অবস্থায় আরও একটি চেক চালান।
mc alias set defaultcheck http://127.0.0.1:9000 minioadmin minioadminএই কমান্ডটি অবশ্যই ব্যর্থ হতে হবে। যদি এটি সফল হয়, তবে এনভায়রনমেন্ট ফাইলটি প্রসেসের কাছে পৌঁছায়নি এবং আপনার সার্ভারটি ডিফল্ট ক্রেডেনশিয়াল ব্যবহার করে চলছে। মেশিনে অন্য কিছু করার আগে এটি ঠিক করুন।
mc অ্যালিয়াসগুলোকে ~/.mc/config.json-এ প্লেইন টেক্সট হিসেবে সংরক্ষণ করে, তাই সেই ক্রেডেনশিয়ালগুলো যে ব্যবহারকারী কমান্ডটি চালিয়েছেন তার হোম ডিরেক্টরিতে থেকে যায়। sudo ব্যবহারকারীর অধীনে mc চালানো হলে রুট ক্রেডেনশিয়ালগুলো /root/.mc/config.json-এ জমা হয়। রুট অ্যালিয়াসটি শুধুমাত্র একজন অ্যাডমিনিস্ট্রেটরের অ্যাকাউন্টে রাখুন এবং প্রতিটি অ্যাপ্লিকেশনের জন্য আলাদা কি (key) প্রদান করুন।
একটি প্রি-সাইনড URL-এর মাধ্যমে একটি অবজেক্ট প্রদান করা
একটি প্রি-সাইনড URL হলো একটি সাধারণ HTTPS লিঙ্ক, যার সাথে একটি সিগনেচার এবং একটি মেয়াদ যুক্ত থাকে। এই লিঙ্কটি যার কাছে থাকবে, তিনি কোনো অ্যাকাউন্ট বা ক্লায়েন্ট ছাড়াই সেই নির্দিষ্ট অবজেক্টটি সংগ্রহ করতে পারবেন।
mc share download --expire 12h local/backups/hello.txtআউটপুটটিতে কুয়েরি স্ট্রিং হিসেবে X-Amz-Signature এবং X-Amz-Expires থাকে। এটি নিয়ে দুটি বিষয় ব্যবহারকারীদের অবাক করে। লিঙ্কটি আপনার ব্যবহৃত অ্যালিয়াসের এন্ডপয়েন্ট থেকে তৈরি হয়, তাই 127.0.0.1-এ থাকা কোনো অ্যালিয়াস এমন একটি লিঙ্ক তৈরি করবে যা শুধুমাত্র এই মেশিন থেকেই খোলা সম্ভব: আপনি যে লিঙ্কগুলো পাঠাতে চান, সেগুলোর জন্য আপনার পাবলিক হোস্টনামে একটি দ্বিতীয় অ্যালিয়াস তৈরি করুন। এছাড়া, এটি বাতিল করার কোনো বাটন নেই। সিগনেচারটি মেয়াদ শেষ না হওয়া পর্যন্ত কার্যকর থাকে, তাই স্বল্পমেয়াদী মেয়াদ নির্ধারণই আপনার একমাত্র নিয়ন্ত্রণ ব্যবস্থা। S3 সিগনেচার ফরম্যাট অনুযায়ী সর্বোচ্চ সাত দিনের মেয়াদ নির্ধারণ করা সম্ভব।
restic-এর জন্য নিজস্ব কি এবং বাকেট তৈরি করুন
root ক্রেডেনশিয়াল দিয়ে প্রতিটি বাকেট পড়া এবং মুছে ফেলা যায়, তাই ব্যাকআপ জবের কাছে এই ক্রেডেনশিয়াল থাকা উচিত নয়। একটি বাকেট তৈরি করুন, সেই বাকেটের জন্য একটি পলিসি নির্ধারণ করুন এবং এমন একজন ইউজার তৈরি করুন যার অন্য কোনো অ্যাক্সেস নেই।
mc mb local/restic
cat > /tmp/restic-rw.json <<'EOF'
{
"Version": "2012-10-17",
"Statement": [
{
"Effect": "Allow",
"Action": ["s3:ListBucket", "s3:GetBucketLocation"],
"Resource": ["arn:aws:s3:::restic"]
},
{
"Effect": "Allow",
"Action": ["s3:GetObject", "s3:PutObject", "s3:DeleteObject"],
"Resource": ["arn:aws:s3:::restic/*"]
}
]
}
EOF
RESTIC_KEY=$(openssl rand -base64 24)
mc admin policy create local restic-rw /tmp/restic-rw.json
mc admin user add local restic-backup "$RESTIC_KEY"
mc admin policy attach local restic-rw --user restic-backupMinIO-তে একটি বিল্ট-ইন readwrite পলিসি থাকে যা দিয়ে কাজ কিছুটা সহজ হতো, কিন্তু সেটি সার্ভারের প্রতিটি বাকেটে পূর্ণ অ্যাক্সেস প্রদান করে। উপরের পলিসিতে বাকেটের নাম দুইবার উল্লেখ করা হয়েছে: একবার arn:aws:s3:::restic হিসেবে যাতে বাকেট লিস্ট করা যায় এবং একবার arn:aws:s3:::restic/* হিসেবে যাতে এর ভেতরের অবজেক্টগুলো অ্যাক্সেস করা যায়। S3-তে একটি বাকেট এবং এর ভেতরের অবজেক্টগুলো আলাদা রিসোর্স হিসেবে গণ্য হয়, তাই পলিসিতে যদি কেবল একটির নাম থাকে তবে তা কাজ করবে না এবং মনে হবে ক্লায়েন্টটি নষ্ট হয়ে গেছে।
নির্ভর করার আগে সীমাবদ্ধতা পরীক্ষা করে নিন।
mc alias set resticuser http://127.0.0.1:9000 restic-backup "$RESTIC_KEY"
mc ls resticuser/restic
mc ls resticuser/backupsপ্রথম ls কমান্ডটি সফল হবে এবং দ্বিতীয়টি Access Denied এর কারণে ব্যর্থ হবে। যে পলিসি আপনি পরীক্ষা করেননি, সেটি কেবল একটি অনুমান।
এখন restic-কে বাকেটের দিকে নির্দেশ করুন। restic স্ট্যান্ডার্ড AWS এনভায়রনমেন্ট ভেরিয়েবল থেকে S3 ক্রেডেনশিয়াল পড়ে, তাই এখানে restic-এর নিজস্ব কোনো ক্রেডেনশিয়াল ফাইলের প্রয়োজন নেই।
sudo apt install -y restic
export AWS_ACCESS_KEY_ID=restic-backup
export AWS_SECRET_ACCESS_KEY="$RESTIC_KEY"
restic -r s3:http://127.0.0.1:9000/restic init
restic -r s3:http://127.0.0.1:9000/restic backup /etc
restic -r s3:http://127.0.0.1:9000/restic snapshotsrestic init একটি রিপোজিটরি পাসওয়ার্ড চাইবে। এই পাসওয়ার্ড দিয়ে রিপোজিটরি এনক্রিপ্ট করা হয়, তাই MinIO শুধুমাত্র সাইফারটেক্সট সংরক্ষণ করে। পাসওয়ার্ড হারিয়ে ফেললে ব্যাকআপও হারিয়ে যাবে। systemd টাইমার দিয়ে শুরু করা কোনো প্রসেসে টাইপ করার জন্য টার্মিনাল থাকে না, তাই শিডিউল করা ব্যাকআপের জন্য RESTIC_PASSWORD_FILE কে মোড 600 ফাইলে সেট করুন।
উপরের যেকোনো কমান্ডের চেয়ে একটি প্লেসমেন্ট রুল বেশি গুরুত্বপূর্ণ। যে ডেটা আপনি রক্ষা করছেন, সেই একই VPS-এ restic রিপোজিটরি রাখলে তা কেবল একটি ভুল rm থেকে আপনাকে বাঁচাতে পারে, অন্য কিছু থেকে নয়। MinIO নোডটি অবশ্যই ভিন্ন একটি মেশিন হতে হবে, আদর্শগতভাবে ভিন্ন কোনো অঞ্চলে। VPS-এ restic ব্যাকআপ অংশে এর পাশাপাশি শিডিউলিং এবং রিটেনশন নিয়ে আলোচনা করা হয়েছে।
nginx দিয়ে TLS টার্মিনেট করা
MinIO লোকালহোস্টে থাকে, তাই nginx হলো পাবলিক ইন্টারফেস। প্রথমে certbot এবং nginx দিয়ে Let's Encrypt সার্টিফিকেট-এ বর্ণিত পদ্ধতি অনুযায়ী সার্টিফিকেট ইস্যু করুন, তারপর এই সার্ভার ব্লকটি ব্যবহার করুন।
server {
listen 443 ssl;
server_name s3.example.com;
ignore_invalid_headers off;
client_max_body_size 0;
proxy_buffering off;
proxy_request_buffering off;
location / {
proxy_set_header Host $http_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_connect_timeout 300;
proxy_http_version 1.1;
proxy_set_header Connection "";
chunked_transfer_encoding off;
proxy_pass http://127.0.0.1:9000;
}
}এই লাইনগুলোর মধ্যে কয়েকটি অত্যন্ত গুরুত্বপূর্ণ। client_max_body_size 0 ডিফল্ট 1 MB বডি লিমিট সরিয়ে ফেলে, অন্যথায় MinIO অনুরোধটি পাওয়ার আগেই 413 Request Entity Too Large এর মাধ্যমে বড় আকারের আপলোড প্রত্যাখ্যান করে। proxy_request_buffering off আপলোড সরাসরি স্ট্রিম করে, কারণ ডিফল্ট কনফিগারেশনে পুরো অনুরোধটি প্রথমে একটি টেম্পোরারি ফাইলে জমা হয় এবং বড় অবজেক্টের ক্ষেত্রে দ্বিগুণ ডিস্ক স্পেসের প্রয়োজন হয়। proxy_set_header Host $http_host একটি সূক্ষ্ম বিষয়: একটি S3 সিগনেচার Host হেডারকে কভার করে, তাই কোনো প্রক্সি যদি এটি পরিবর্তন করে তবে প্রতিটি অনুরোধ SignatureDoesNotMatch এর মাধ্যমে ব্যর্থ হয়, যদিও এক্সেস লগে অনুরোধটি স্বাভাবিকভাবে আসার তথ্য দেখা যায়।
MinIO-কে তার পাবলিক নামটিও জানিয়ে দিন, যাতে এটি যে লিঙ্কগুলো তৈরি করে তা লোকালহোস্টের পরিবর্তে প্রক্সিকে নির্দেশ করে।
echo 'MINIO_SERVER_URL=https://s3.example.com' | sudo tee -a /etc/default/minio
sudo systemctl restart minioফায়ারওয়াল ছোট রাখুন। SSH এবং HTTPS-এর অনুমতি দিন, এবং 9000 ও 9001 পোর্টগুলোর জন্য কোনো রুল সেট করবেন না, কারণ 127.0.0.1-এ বাইন্ড করা অ্যাড্রেস ফায়ারওয়াল যাই বলুক না কেন, অন্য কোনো মেশিন থেকে অ্যাক্সেস করা সম্ভব নয়। VPS-এ ufw ফায়ারওয়ালের মৌলিক বিষয়সমূহ-এ কমান্ডগুলো দেওয়া আছে।
কখন সিঙ্গেল-নোড MinIO যথেষ্ট এবং কখন আপনার প্রকৃত S3 প্রয়োজন
এখানে সিঙ্গেল-নোড বলতে বোঝানো হয়েছে একটি ড্রাইভ যেখানে কোনো প্যারিটি (parity) নেই। MinIO-এর নিজস্ব ডকুমেন্টেশনে এই লেআউটটিকে টেস্টিং এবং ছোটখাটো কাজের জন্য উপযুক্ত বলা হয়েছে, যেখানে কোনো অ্যাভেইল্যাবিলিটি বা প্রাপ্যতা নিশ্চিত করার প্রয়োজন নেই। এই ডিপ্লয়মেন্টের ভেতরে কোনো দ্বিতীয় কপি থাকে না, তাই প্রতিটি অবজেক্টের স্থায়িত্ব একটি VPS ডিস্কের স্থায়িত্বের সমান। ডিস্ট্রিবিউটেড ইরেজার-কোডেড ব্যাকএন্ডের ওপর নির্ভরশীল ফিচারগুলো, যেমন বাকেট রেপ্লিকেশন (bucket replication) এবং অবজেক্ট লকিং (object locking), শুধুমাত্র মাল্টি-ড্রাইভ ডিপ্লয়মেন্টে কাজ করে। তাই এই সেটআপে কাউকে ইমিউটেবল রিটেনশন পলিসির নিশ্চয়তা দেবেন না।
অন্য কোনো অঞ্চলে অবস্থিত দ্বিতীয় একটি VPS-এ restic টার্গেট হিসেবে এটি ব্যবহার করা ভালো। এছাড়া ডেভেলপমেন্ট কাজ এবং CI আর্টিফ্যাক্টের জন্য S3 এন্ডপয়েন্ট হিসেবে এটি উপযুক্ত, যেখানে একটি বাকেট হারিয়ে গেলে পুনরায় তৈরি করা ছাড়া বড় কোনো ক্ষতি হয় না। ছোট অ্যাপ্লিকেশনে ব্যবহারকারীর আপলোডের জন্য এটি যুক্তিসঙ্গত, যদি আপনার কাছে রিকভারি প্ল্যান থাকে এবং আপনি বাস্তবে তা পরীক্ষা করে দেখে থাকেন।
যখন কোনো চুক্তি বা রেগুলেটর অবজেক্ট লক বা মাল্টি-রিজিয়ন ডিউরেবিলিটির দাবি জানায়, তখন ম্যানেজড S3 বেছে নিন। অথবা যদি আপনি এমন কেউ হতে না চান যাকে রাত 3টার সময় ডিস্ক পূর্ণ হয়ে যাওয়ার কারণে কল করা হবে, তবে ম্যানেজড S3 ব্যবহার করুন। ফ্রোজেন বিল্ড (frozen build) আরেকটি বাস্তব কারণ। জুলাই 2026 অনুযায়ী, প্রি-কম্পাইলড কমিউনিটি বাইনারিটি সেপ্টেম্বর 2025 সালের এবং এতে কোনো ফিক্স দেওয়া হয় না। তাই এটি চালানোর অর্থ হলো এই সীমাবদ্ধতা মেনে নেওয়া, অথবা সোর্স থেকে বিল্ড করে নিজে প্রজেক্টের আপডেট বজায় রাখা।
একটি সীমানা উল্লেখ করা প্রয়োজন কারণ এটি প্রায়ই সামনে আসে। অবজেক্ট স্টোরেজ কোনো ডাটাবেস নয়। প্রতিটি রাইট অপারেশন একটি সম্পূর্ণ অবজেক্টকে প্রতিস্থাপন করে, তাই S3 বাকেটে সরাসরি SQL ফাইল রাখা ধীরগতির এবং অনিরাপদ। ডাটাবেসটি লোকাল ডিস্কে রাখুন এবং সেটির ব্যাকআপ বাকেটে রাখুন: VPS-এ প্রোডাকশনে SQLite চালানো এই বিভাজনটি বর্ণনা করে।
ব্যর্থতার ধরন এবং যে বার্তাগুলো আপনি দেখবেন
systemctl enable --now-এর ঠিক পরেই ইউনিটটি ব্যর্থ হয়। journalctl -u minio -n 30 --no-pager পড়ুন। Failed to load environment files: No such file or directory মানে হলো /etc/default/minio অনুপস্থিত অথবা ইউনিটে এর পাথ ভুলভাবে লেখা হয়েছে। permission denied দিয়ে শেষ হওয়া কোনো বার্তার মানে হলো সার্ভিস অ্যাকাউন্টটির ডেটা ডিরেক্টরিতে লেখার অনুমতি নেই, তাই নিশ্চিত করুন যে stat -c '%U' /var/lib/minio/data কমান্ডটি minio-user আউটপুট দিচ্ছে।
minioadmin:minioadmin এখনও লগইন করতে পারছে। এনভায়রনমেন্ট ফাইলটি প্রসেসের কাছে পৌঁছায়নি। নিশ্চিত করুন যে ইউনিটে EnvironmentFile=/etc/default/minio আছে, sudo systemctl daemon-reload কমান্ডটি চালান, এবং তারপর সার্ভিসটি রিস্টার্ট করুন। MinIO স্টার্টআপের সময় একবারই রুট ক্রেডেনশিয়াল পড়ে, তাই রিস্টার্ট না করে ফাইলটি এডিট করলে কোনো পরিবর্তন হবে না।
স্টার্টআপের সময় Address already in use। অন্য কোনো প্রসেস 9000 পোর্টটি দখল করে রেখেছে। MinIO-এর পোর্ট পরিবর্তন করার আগে sudo ss -ltnp | grep :9000 ব্যবহার করে সেই প্রসেসটি খুঁজে বের করুন।
প্রক্সির মাধ্যমে 1 MB-এর বেশি সাইজের ফাইল আপলোড ব্যর্থ হচ্ছে। nginx 413 Request Entity Too Large উত্তর দিয়েছে এবং MinIO অনুরোধটি পায়নি। সার্ভার ব্লকে client_max_body_size 0 সেট করুন।
SignatureDoesNotMatch। হয় সিক্রেট কি ভুল, অথবা ক্লায়েন্ট এবং MinIO-এর মধ্যবর্তী কোনো কিছু Host হেডারটি পরিবর্তন করেছে, যা সিগনেচারের অন্তর্ভুক্ত।
RequestTimeTooSkewed। ক্লায়েন্ট বা সার্ভারের ঘড়ির সময় ভুল। প্রতিটি S3 অনুরোধে একটি টাইমস্ট্যাম্প থাকে এবং 15 মিনিটের উইন্ডোর বাইরে হলে তা প্রত্যাখ্যান করা হয়। timedatectl চেক করুন এবং নিশ্চিত করুন যে টাইম সিনক্রোনাইজেশন সচল আছে।
আপনার জানা কোনো বাকেটে Access Denied। কি (key)-টি অন্য কোনো বাকেটের জন্য নির্ধারিত। mc admin policy info local restic-rw ব্যবহার করে পলিসিটি আসলে কী অনুমতি দিচ্ছে তা দেখুন এবং রিসোর্স লাইনে বাকেটের নামের সাথে মিলিয়ে দেখুন।
FAQ
সিঙ্গেল-নোড MinIO কি প্রকৃত ব্যাকআপের জন্য যথেষ্ট?
এটি একটি আলাদা মেশিনে restic টার্গেট হিসেবে চালানোর জন্য যথেষ্ট, যা আপনার ডেটা সুরক্ষিত রাখে। তবে এটি আপনার একমাত্র কপি হিসেবে যথেষ্ট নয়। একটি সিঙ্গেল-ড্রাইভ ডেপ্লয়মেন্টে কোনো প্যারিটি থাকে না, তাই MinIO-এর ভেতরে কোনো দ্বিতীয় কপি থাকে না। যদি সেই VPS ডিস্কের ডেটা হারিয়ে যায়, তবে অবজেক্টগুলোও মুছে যাবে। অন্য কোথাও একটি দ্বিতীয় টার্গেট রাখুন এবং অন্তত একবার উভয় জায়গা থেকে রিস্টোর করে দেখুন, যাতে আপনি নিশ্চিত হতে পারেন যে প্রক্রিয়াটি কাজ করছে।
sha256sum -c কেন MinIO-এর চেকসাম ফাইলে ব্যর্থ হয়?
কারণ সেই ফাইলের ভেতরে হ্যাশের পরের লেবেলটি রিলিজের নাম নির্দেশ করে, যা হলো minio.RELEASE.2025-09-07T16-13-09Z, অথচ আপনার ডাউনলোড করা ফাইলটির নাম সাধারণত minio। sha256sum -c চেকসাম ফাইলের ভেতরে লেখা নামের ফাইলটি খোঁজে, সেটি না পেয়ে No such file or directory এবং WARNING: 1 listed file could not be read রিপোর্ট করে। ডাউনলোডটি সঠিক আছে। সরাসরি হ্যাশ স্ট্রিংগুলো তুলনা করুন এবং লেবেলটি উপেক্ষা করুন, কারণ এর কোনো নিরাপত্তা সংক্রান্ত গুরুত্ব নেই।
MinIO অ্যাডমিন ওয়েব কনসোল কোথায় গেল?
MinIO মে 2025 সালে কমিউনিটি এডিশন কনসোল থেকে অ্যাডমিনিস্ট্রেশন ফিচারগুলো সরিয়ে নিয়েছে, ওয়েব ইন্টারফেসে কেবল একটি অবজেক্ট ব্রাউজার রাখা হয়েছে। বাকেট এবং ইউজাররা এখন mc ক্লায়েন্টের মাধ্যমে পরিচালিত হয়, যেখানে mc admin user add এবং mc admin policy attach এর মতো কমান্ড ব্যবহার করা হয়। কমিউনিটি এডিশনে এটিই সমর্থিত পদ্ধতি, কোনো বিকল্প সমাধান নয়; আর এই কারণেই এই গাইডে সবকিছু কমান্ড লাইন থেকে করা হয়েছে।
আমি কীভাবে restic-কে S3 ব্যাকএন্ড হিসেবে MinIO-এর দিকে নির্দেশ করব?
AWS_ACCESS_KEY_ID এবং AWS_SECRET_ACCESS_KEY কে একটি MinIO অ্যাক্সেস কি এবং এর সিক্রেট হিসেবে সেট করুন, তারপর s3:https://s3.example.com/restic ফরম্যাটের একটি রিপোজিটরি স্ট্রিং ব্যবহার করুন, যেখানে শেষ পাথ এলিমেন্টটি হলো বাকেটের নাম। প্রথমে mc mb দিয়ে বাকেটটি তৈরি করুন, কারণ একটি নির্দিষ্ট বাকেটের জন্য সীমাবদ্ধ কি-এর বাকেট তৈরি করার অনুমতি থাকে না। restic আপলোডের আগে তার নিজস্ব রিপোজিটরি পাসওয়ার্ড দিয়ে সবকিছু এনক্রিপ্ট করে, তাই MinIO সাইফারটেক্সট সংরক্ষণ করে এবং আপনার ফাইলগুলো কখনোই দেখতে পায় না।
আমাকে কি nginx-এর পেছনে MinIO চালাতে হবে?
যখন কোনো ক্লায়েন্ট একই মেশিনে থাকে না, তখন আপনার TLS (transport layer security) প্রয়োজন, কারণ S3 ক্রেডেনশিয়াল এবং অবজেক্ট ডেটা উভয়ই রিকোয়েস্টের ভেতরে যাতায়াত করে। certbot থেকে পাওয়া সার্টিফিকেটসহ পোর্ট 443-এ একটি প্রক্সি ব্যবহার করা এটি পাওয়ার সবচেয়ে সহজ উপায় এবং এটি সার্টিফিকেট রিনিউয়ালকে MinIO থেকে দূরে রাখে। MinIO নিজেও TLS টার্মিনেট করতে পারে যদি আপনি --certs-dir কে এমন একটি ডিরেক্টরির দিকে নির্দেশ করেন যেখানে public.crt এবং private.key রাখা আছে, কিন্তু সেক্ষেত্রে সার্ভিস অ্যাকাউন্টের রিনিউ করা প্রাইভেট কি-তে রিড অ্যাক্সেস প্রয়োজন হয়, যা একই ফলাফলের জন্য বাড়তি কাজ।