{"id":35748,"date":"2026-01-11T17:30:43","date_gmt":"2026-01-11T10:30:43","guid":{"rendered":"https:\/\/dps.media\/giai-phong-du-lieu-huong-dan-di-doi-metabase-docker-volume-sang-vps-moi-2026\/"},"modified":"2026-01-11T17:33:43","modified_gmt":"2026-01-11T10:33:43","slug":"liberate-data-guide-to-migrating-metabase-docker-volume-to-new-vps-2026","status":"publish","type":"post","link":"https:\/\/dps.media\/en\/liberate-data-guide-to-migrating-metabase-docker-volume-to-new-vps-2026\/","title":{"rendered":"Data Liberation: Guide to Migrating Metabase (Docker Volume) to New VPS 2026"},"content":{"rendered":"<p>Have you ever moved a complex Supabase system, and now it's time to face the next challenge: <strong>Metabase<\/strong>. While Supabase stores data clearly in bind-mount folders, Metabase by default hides data deeply in <strong>Docker Volumes<\/strong> invisible ones. This makes backup or migration to a new VPS more \u201cchallenging\u201d for non-experts.<\/p>\n\n\n\n<p>In this article, we will solve the problem: How to \u201cextract\u201d all Metabase data (Charts, Dashboard, Users) from a deeply hidden Docker Volume on the old VPS to a brand new VPS, and especially convert it to Folder (Bind Mount) format for easy management forever after.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Problem: \u201cInvisible\u201d Data (Docker Volumes)<\/h2>\n\n\n\n<p>When you install Metabase with the command <code>docker run<\/code> or sample compose files online, data is often stored in Docker Volume (Managed Volume). You won't see it when <code>ls \/opt<\/code> or <code>ls \/home<\/code>. It lies deep in <code>\/var\/lib\/docker\/volumes\/...<\/code>.<\/p>\n\n\n<div class=\"wp-block-image\">\n<figure class=\"aligncenter size-large\"><img decoding=\"async\" src=\"https:\/\/dps.media\/wp-content\/uploads\/mcp\/2026\/01\/volume_to_folder_concept_1768127348760.jpg\" alt=\"Convert Docker Volume to Local Folder\" title=\"\"><figcaption>Strategy: Switch from closed Volume to open Folder<\/figcaption><\/figure>\n<\/div>\n\n\n<p>This causes difficulty when you want to backup (must use specific volume backup command) or edit config directly. Our strategy today is: <strong>Release the data<\/strong>.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Step 1: \u201cDetective\u201d Docker \u2013 Find Data &amp; Password<\/h2>\n\n\n\n<p>Before migrating, you must know where the data is and the key (password) to unlock it. Many cases after migration forget the old database password, leading to the new Metabase unable to read the data.<\/p>\n\n\n<p>At <strong>Old VPS<\/strong>, use the command <code>docker inspect<\/code> to inspect the information:<\/p>\n\n\n<div class=\"wp-block-image\">\n<figure class=\"aligncenter size-large\"><img decoding=\"async\" src=\"https:\/\/dps.media\/wp-content\/uploads\/mcp\/2026\/01\/docker_inspect_secrets_1768127332437.jpg\" alt=\"Use Docker Inspect to Find Password\" title=\"\"><figcaption>Find the hidden Database password in environment variables<\/figcaption><\/figure>\n<\/div>\n\n\n<pre class=\"wp-block-code\"><code># 1. Find Database password (Most important!)\ndocker inspect -f '{{range .Config.Env}}{{println .}}{{end}}' metabase_container_name | grep MB_DB_PASS\n\n# 2. Determine exact Volume path\ndocker inspect -f '{{ json .Mounts }}' metabase_db_container_name<\/code><\/pre>\n\n\n\n<p>Please note the password string (e.g.: <code>ExAmPlE_P@ssw0rd...<\/code>) and the source volume path (e.g.: <code>\/var\/lib\/docker\/volumes\/metabase_data\/_data<\/code>). We will need them in the next step.<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Step 2: Rsync \u2013 Data Migration<\/h2>\n\n\n\n<p>After determining the \u201chome address\u201d of the data on the old VPS, we will use <code>rsync<\/code> to transfer it directly to the new VPS. On the new VPS, we will create a proper folder to receive it.<\/p>\n\n\n\n<p><strong>On New VPS:<\/strong><\/p>\n\n\n<pre class=\"wp-block-code\"><code>mkdir -p \/opt\/metabase\/pgdata<\/code><\/pre>\n\n\n\n<p><strong>On Old VPS (Run rsync command):<\/strong><\/p>\n\n\n<pre class=\"wp-block-code\"><code># Note: source path taken from step 1\n# IP_VPS_NEW: Replace with new server IP\n\nrsync -avzP \/var\/lib\/docker\/volumes\/metabase_data\/_data\/ root@IP_VPS_NEW:\/opt\/metabase\/pgdata\/<\/code><\/pre>\n\n\n\n<p>At this point, all your precious data is safely in the folder <code>\/opt\/metabase\/pgdata<\/code> on the new server. It has become physical files that you can see, copy, and backup easily!<\/p>\n\n\n\n<h2 class=\"wp-block-heading\">Step 3: Build New House (Docker Compose Clean Setup)<\/h2>\n\n\n\n<p>Instead of reusing the old messy configuration, we will write a new file <code>docker-compose.yml<\/code> clean, beautiful, and more standard. This file will connect the Metabase Application to the Database data we just transferred.<\/p>\n\n\n<div class=\"wp-block-image\">\n<figure class=\"aligncenter size-large\"><img decoding=\"async\" src=\"https:\/\/dps.media\/wp-content\/uploads\/mcp\/2026\/01\/metabase_compose_structure_1768127364396.jpg\" alt=\"New Metabase Docker Compose Structure\" title=\"\"><figcaption>Connection model: App -&gt; Database -&gt; Local Folder<\/figcaption><\/figure>\n<\/div>\n\n\n<p>Create file <code>\/opt\/metabase\/docker-compose.yml<\/code> with the following content (Remember to replace PASSWORD with the pass you found in Step 1):<\/p>\n\n\n\n<pre class=\"wp-block-code\"><code>version: '3.9'\nservices:\n  metabase:\n    image: metabase\/metabase:latest\n    container_name: metabase\n    restart: unless-stopped\n    ports:\n      - \"3000:3000\"\n    environment:\n      MB_DB_TYPE: postgres\n      MB_DB_DBNAME: metabase\n      MB_DB_PORT: 5432\n      MB_DB_USER: metabase\n      MB_DB_PASS: YOUR_SECRET_PASSWORD_HERE\n      MB_DB_HOST: metabase-db\n    depends_on:\n      - metabase-db\n\n  metabase-db:\n    image: postgres:15\n    container_name: metabase-db\n    restart: unless-stopped\n    environment:\n      POSTGRES_USER: metabase\n      POSTGRES_DB: metabase\n      POSTGRES_PASSWORD: YOUR_SECRET_PASSWORD_HERE\n    volumes:\n      # MOST IMPORTANT CONNECTION:\n      # Mount the rsynced data folder into the database\n      - .\/pgdata:\/var\/lib\/postgresql\/data<\/code><\/pre>\n\n\n\n<p>Then start it:<\/p>\n\n\n<pre class=\"wp-block-code\"><code>docker compose up -d<\/code><\/pre>\n\n\n\n<h2 class=\"wp-block-heading\">Step 4: Domain &amp; SSL Configuration<\/h2>\n\n\n\n<p>Using <strong>Nginx Proxy Manager<\/strong> (which you installed in the previous guide) to expose Metabase to the internet securely.<\/p>\n\n\n\n<ul class=\"wp-block-list\">\n<li><strong>Domain:<\/strong> <code>data.your-domain.com<\/code><\/li>\n<li><strong>Forward IP:<\/strong> <code>172.17.0.1<\/code><\/li>\n<li><strong>Forward Port:<\/strong> <code>3000<\/code><\/li>\n<li><strong>SSL:<\/strong> Let\u2019s Encrypt (Force SSL)<\/li>\n<\/ul>\n\n\n<div class=\"wp-block-image\">\n<figure class=\"aligncenter size-large\"><img decoding=\"async\" src=\"https:\/\/dps.media\/wp-content\/uploads\/mcp\/2026\/01\/metabase_success_dashboard_1768127381275.jpg\" alt=\"Metabase Runs Successfully on New VPS\" title=\"\"><figcaption>The system works perfectly, dashboard data remains intact<\/figcaption><\/figure>\n<\/div>\n\n\n<h2 class=\"wp-block-heading\">Conclusion<\/h2>\n\n\n\n<p>Converting from Docker Managed Volume to Bind Mount (Folder) not only helps you migrate successfully but is also a major upgrade for system administration. From now on, backing up Metabase data is as simple as copying the folder <code>\/opt\/metabase\/pgdata<\/code>.<\/p>\n\n\n\n<p>Wishing you a powerful and stable Business Intelligence system in your new home!<\/p>\n<style>\r\n.lwrp.link-whisper-related-posts{\r\n            \r\n            margin-top: 40px;\nmargin-bottom: 30px;\r\n        }\r\n        .lwrp .lwrp-title{\r\n            \r\n            \r\n        }.lwrp .lwrp-description{\r\n            \r\n            \r\n\r\n        }\r\n        .lwrp .lwrp-list-container{\r\n        }\r\n        .lwrp .lwrp-list-multi-container{\r\n            display: flex;\r\n        }\r\n        .lwrp .lwrp-list-double{\r\n            width: 48%;\r\n        }\r\n        .lwrp .lwrp-list-triple{\r\n            width: 32%;\r\n        }\r\n        .lwrp .lwrp-list-row-container{\r\n            display: flex;\r\n            justify-content: space-between;\r\n        }\r\n        .lwrp .lwrp-list-row-container .lwrp-list-item{\r\n            width: calc(33% - 20px);\r\n        }\r\n        .lwrp .lwrp-list-item:not(.lwrp-no-posts-message-item){\r\n            \r\n            max-width: 150px;\r\n        }\r\n        .lwrp .lwrp-list-item img{\r\n            max-width: 100%;\r\n            height: auto;\r\n            object-fit: cover;\r\n            aspect-ratio: 1 \/ 1;\r\n        }\r\n        .lwrp .lwrp-list-item.lwrp-empty-list-item{\r\n            background: initial !important;\r\n        }\r\n        .lwrp .lwrp-list-item .lwrp-list-link .lwrp-list-link-title-text,\r\n        .lwrp .lwrp-list-item .lwrp-list-no-posts-message{\r\n            \r\n            \r\n            \r\n            \r\n        }@media screen and (max-width: 480px) {\r\n            .lwrp.link-whisper-related-posts{\r\n                \r\n                \r\n            }\r\n            .lwrp .lwrp-title{\r\n                \r\n                \r\n            }.lwrp .lwrp-description{\r\n                \r\n                \r\n            }\r\n            .lwrp .lwrp-list-multi-container{\r\n                flex-direction: column;\r\n            }\r\n            .lwrp .lwrp-list-multi-container ul.lwrp-list{\r\n                margin-top: 0px;\r\n                margin-bottom: 0px;\r\n                padding-top: 0px;\r\n                padding-bottom: 0px;\r\n            }\r\n            .lwrp .lwrp-list-double,\r\n            .lwrp .lwrp-list-triple{\r\n                width: 100%;\r\n            }\r\n            .lwrp .lwrp-list-row-container{\r\n                justify-content: initial;\r\n                flex-direction: column;\r\n            }\r\n            .lwrp .lwrp-list-row-container .lwrp-list-item{\r\n                width: 100%;\r\n            }\r\n            .lwrp .lwrp-list-item:not(.lwrp-no-posts-message-item){\r\n                \r\n                max-width: initial;\r\n            }\r\n            .lwrp .lwrp-list-item .lwrp-list-link .lwrp-list-link-title-text,\r\n            .lwrp .lwrp-list-item .lwrp-list-no-posts-message{\r\n                \r\n                \r\n                \r\n                \r\n            };\r\n        }<\/style>\r\n<div id=\"link-whisper-related-posts-widget\" class=\"link-whisper-related-posts lwrp\">\r\n            <div class=\"lwrp-title\">Related Posts<\/div>    \r\n        <div class=\"lwrp-list-container\">\r\n                                <div class=\"lwrp-list lwrp-list-row-container lwrp-list-double-row\">\r\n                <div class=\"lwrp-list-item\"><a href=\"https:\/\/dps.media\/en\/design-catalogue-with-powerpoint-for-beginners-to-create-beautiful-templates-without-cost\/\" class=\"lwrp-list-link\"><span class=\"lwrp-list-link-title-text\">Designing a catalogue with PowerPoint for beginners \u2013 Creating beautiful templates without extra cost<\/span><\/a><\/div><div class=\"lwrp-list-item\"><a href=\"https:\/\/dps.media\/en\/how-to-livestream-on-facebook-to-sell-products-and-reach-1000-first-views\/\" class=\"lwrp-list-link\"><span class=\"lwrp-list-link-title-text\">How to livestream on Facebook to achieve 1000 views on the first broadcast<\/span><\/a><\/div><div class=\"lwrp-list-item\"><a href=\"https:\/\/dps.media\/en\/dps-media-recruiting-part-time-sales-intern\/\" class=\"lwrp-list-link\"><span class=\"lwrp-list-link-title-text\">DPS.MEDIA RECRUITS INTERN &amp; PART-TIME SALES\u00a0<\/span><\/a><\/div>                <\/div>\r\n                            <div class=\"lwrp-list lwrp-list-row-container lwrp-list-double-row\">\r\n                <div class=\"lwrp-list-item\"><a href=\"https:\/\/dps.media\/en\/what-is-canva-a-to-z-guide-on-how-to-use-canva\/\" class=\"lwrp-list-link\"><span class=\"lwrp-list-link-title-text\">What is Canva? A Complete Guide to Using Canva from A to Z\u00a0<\/span><\/a><\/div><div class=\"lwrp-list-item\"><a href=\"https:\/\/dps.media\/en\/safe-facebook-organic-reach-boosting-service\/\" class=\"lwrp-list-link\"><span class=\"lwrp-list-link-title-text\">Safe Facebook Organic Reach Increase Service<\/span><\/a><\/div><div class=\"lwrp-list-item\"><a href=\"https:\/\/dps.media\/en\/are-there-best-practices-for-email-preheaders-that-you-know\/\" class=\"lwrp-list-link\"><span class=\"lwrp-list-link-title-text\">Are there best practices for E-mail Preheader, do you know?<\/span><\/a><\/div>                <\/div>\r\n                <\/div>\r\n<\/div>","protected":false},"excerpt":{"rendered":"<p>Have you ever migrated a complex Supabase system, and now it's time to face the next challenge: Metabase. While Supabase stores data clearly in bind-mount folders, Metabase by default hides data thoroughly in invisible Docker Volumes. This makes [\u2026]<\/p>","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"","sticky":false,"template":"","format":"standard","meta":{"_acf_changed":false,"footnotes":""},"categories":[1],"tags":[],"class_list":["post-35748","post","type-post","status-publish","format-standard","hentry","category-uncategorized"],"acf":[],"rankmath_keywords":{"primary":"","secondary":[""]},"yoast_keywords":{"primary":"","secondary":[]},"yoast_focuskw":"","rankmath_focuskw":"","seo_keywords":{"primary":"","secondary":[""]},"_links":{"self":[{"href":"https:\/\/dps.media\/en\/wp-json\/wp\/v2\/posts\/35748","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/dps.media\/en\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/dps.media\/en\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/dps.media\/en\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/dps.media\/en\/wp-json\/wp\/v2\/comments?post=35748"}],"version-history":[{"count":1,"href":"https:\/\/dps.media\/en\/wp-json\/wp\/v2\/posts\/35748\/revisions"}],"predecessor-version":[{"id":35749,"href":"https:\/\/dps.media\/en\/wp-json\/wp\/v2\/posts\/35748\/revisions\/35749"}],"wp:attachment":[{"href":"https:\/\/dps.media\/en\/wp-json\/wp\/v2\/media?parent=35748"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/dps.media\/en\/wp-json\/wp\/v2\/categories?post=35748"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/dps.media\/en\/wp-json\/wp\/v2\/tags?post=35748"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}