PostgreSQL là một hệ quản trị cơ sở dữ liệu đối tượng-quan hệ (ORDBMS) mã nguồn mở vô cùng mạnh mẽ và đáng tin cậy. Tuy nhiên, khi làm việc trên Ubuntu 20.04, bạn có thể nhận thấy thư mục dữ liệu mặc định của nó nằm trên phân vùng hệ thống. Điều này có thể gây ra nhiều vấn đề, từ giới hạn dung lượng lưu trữ đến ảnh hưởng hiệu suất. Bạn đã bao giờ lo lắng về việc ổ đĩa gốc bị đầy và làm sập toàn bộ cơ sở dữ liệu chưa? Di chuyển thư mục dữ liệu sang một vị trí khác, chẳng hạn như một ổ đĩa riêng, là một giải pháp thông minh và cần thiết. Bài viết này sẽ hướng dẫn bạn từng bước chi tiết để thay đổi vị trí thư mục dữ liệu PostgreSQL một cách an toàn và hiệu quả. Chúng ta sẽ cùng nhau tìm hiểu từ lý do cần thay đổi, cách chuẩn bị thư mục mới, quy trình di chuyển dữ liệu, cấu hình lại hệ thống và cách xử lý các sự cố thường gặp.
Lý do cần thay đổi vị trí thư mục lưu trữ dữ liệu PostgreSQL
Việc di chuyển thư mục dữ liệu PostgreSQL ra khỏi vị trí mặc định không chỉ là một thủ thuật kỹ thuật. Đây là một quyết định chiến lược có thể ảnh hưởng lớn đến hiệu suất, khả năng quản lý và độ an toàn của toàn bộ hệ thống cơ sở dữ liệu của bạn. Hãy cùng xem xét kỹ hơn những hạn chế của vị trí mặc định và lợi ích mà việc di chuyển mang lại.
Hạn chế của vị trí mặc định
Vị trí mặc định cho thư mục dữ liệu của PostgreSQL trên Ubuntu thường là /var/lib/postgresql/<version>/main. Vị trí này nằm trên phân vùng gốc (/) của hệ điều hành. Điều này tiềm ẩn hai vấn đề lớn. Thứ nhất là giới hạn về dung lượng. Phân vùng gốc thường có kích thước giới hạn và được chia sẻ với hệ điều hành, các ứng dụng khác và file log. Khi cơ sở dữ liệu của bạn phát triển, nó có thể nhanh chóng chiếm hết dung lượng trống, dẫn đến lỗi và thậm chí làm hệ thống ngừng hoạt động.
Vấn đề thứ hai liên quan đến hiệu suất và quản lý. Việc để dữ liệu PostgreSQL trên cùng ổ đĩa với hệ điều hành có thể tạo ra “nút thắt cổ chai” về I/O (Input/Output). Các hoạt động đọc/ghi của hệ điều hành và của cơ sở dữ liệu sẽ cạnh tranh với nhau, làm giảm tốc độ truy xuất dữ liệu. Hơn nữa, việc quản lý sao lưu, phục hồi và giám sát cũng trở nên phức tạp hơn khi dữ liệu quan trọng nằm chung với các file hệ thống.

Lợi ích khi sử dụng thư mục dữ liệu mới
Chuyển thư mục dữ liệu sang một phân vùng hoặc ổ đĩa riêng biệt mang lại nhiều lợi ích rõ rệt. Đầu tiên và quan trọng nhất là tối ưu hiệu suất truy xuất dữ liệu. Khi cơ sở dữ liệu có một ổ đĩa chuyên dụng, các hoạt động I/O sẽ không bị cạnh tranh, giúp tăng tốc độ đọc/ghi và giảm độ trễ của các truy vấn. Bạn có thể chọn một ổ đĩa có tốc độ cao hơn, như SSD, để tối ưu hóa hơn nữa.
Thứ hai, việc quản lý dung lượng trở nên dễ dàng hơn rất nhiều. Bạn có thể phân bổ một không gian lưu trữ lớn cho cơ sở dữ liệu mà không cần lo lắng về việc ảnh hưởng đến hệ điều hành. Việc theo dõi, mở rộng dung lượng khi cần thiết cũng đơn giản và độc lập. Cuối cùng, di chuyển dữ liệu ra một ổ đĩa riêng giúp tăng cường khả năng bảo mật và sao lưu. Bạn có thể áp dụng các chính sách sao lưu riêng cho ổ đĩa dữ liệu, chẳng hạn như tạo snapshot cấp độ ổ đĩa, mà không cần phải sao lưu toàn bộ hệ điều hành. Điều này giúp quy trình backup và restore nhanh chóng và hiệu quả hơn.
Các bước chuẩn bị thư mục mới trên Ubuntu 20.04
Trước khi tiến hành di chuyển bất kỳ dữ liệu nào, khâu chuẩn bị là cực kỳ quan trọng để đảm bảo quá trình diễn ra suôn sẻ và không gặp lỗi. Chúng ta cần tạo một ngôi nhà mới cho dữ liệu PostgreSQL và chắc chắn rằng nó được thiết lập đúng cách.
Kiểm tra phân vùng và tạo thư mục mới
Bước đầu tiên là xác định vị trí bạn muốn chuyển dữ liệu đến. Đó có thể là một ổ đĩa đã được mount hoặc một phân vùng khác trên hệ thống. Bạn cần đảm bảo rằng vị trí mới có đủ dung lượng trống. Sử dụng lệnh df -h để kiểm tra dung lượng các ổ đĩa và phân vùng hiện có.
df -h

Lệnh này sẽ hiển thị danh sách các hệ thống tệp, dung lượng tổng, dung lượng đã sử dụng, dung lượng còn trống và điểm mount. Dựa vào thông tin này, hãy chọn một vị trí phù hợp, ví dụ, một ổ đĩa được mount tại /mnt/data. Sau khi đã chọn được vị trí, hãy tạo một thư mục mới để chứa dữ liệu PostgreSQL. Ví dụ, chúng ta sẽ tạo thư mục postgresql-data:
sudo mkdir -p /mnt/data/postgresql-data
Lệnh mkdir -p sẽ tạo thư mục và cả các thư mục cha nếu chúng chưa tồn tại, đảm bảo không có lỗi xảy ra.
Phân quyền và bảo mật thư mục
PostgreSQL chạy dưới một người dùng hệ thống riêng biệt tên là postgres. Do đó, thư mục dữ liệu mới phải thuộc sở hữu của người dùng này để dịch vụ có thể đọc và ghi dữ liệu. Nếu không thiết lập quyền đúng cách, PostgreSQL sẽ không thể khởi động. Chúng ta cần thay đổi quyền sở hữu của thư mục vừa tạo.
Sử dụng lệnh chown để gán quyền sở hữu cho người dùng và nhóm postgres:
sudo chown postgres:postgres /mnt/data/postgresql-data
Sau khi gán quyền, bạn nên kiểm tra lại để chắc chắn mọi thứ đã chính xác. Dùng lệnh ls -ld để xem thông tin chi tiết về quyền của thư mục:
ls -ld /mnt/data/postgresql-data

Kết quả trả về phải cho thấy postgres postgres là chủ sở hữu. Ngoài ra, quyền truy cập của thư mục cũng rất quan trọng. Mặc định, PostgreSQL yêu cầu quyền 0700 cho thư mục dữ liệu, nghĩa là chỉ người dùng sở hữu (postgres) mới có toàn quyền đọc, ghi và thực thi. Lệnh chown thường giữ lại các quyền mặc định, nhưng để chắc chắn, bạn có thể đặt lại quyền bằng lệnh chmod:
sudo chmod 700 /mnt/data/postgresql-data
Việc chuẩn bị kỹ lưỡng thư mục mới với quyền truy cập chính xác là chìa khóa để tránh các lỗi không đáng có sau này.
Quy trình di chuyển thư mục dữ liệu PostgreSQL
Khi “ngôi nhà mới” đã sẵn sàng, chúng ta có thể bắt đầu quá trình di chuyển. Quy trình này đòi hỏi sự cẩn thận ở từng bước để đảm bảo tính toàn vẹn của dữ liệu và hệ thống có thể hoạt động trở lại bình thường.
Dừng dịch vụ PostgreSQL an toàn
Tuyệt đối không di chuyển dữ liệu khi cơ sở dữ liệu đang hoạt động. Điều này có thể gây hỏng dữ liệu và làm quá trình di chuyển thất bại. Bước đầu tiên và quan trọng nhất là dừng dịch vụ PostgreSQL một cách an toàn.
Sử dụng lệnh systemctl để dừng dịch vụ:
sudo systemctl stop postgresql
Sau khi chạy lệnh, hãy kiểm tra lại trạng thái của dịch vụ để đảm bảo nó đã dừng hoàn toàn.
sudo systemctl status postgresql

Bạn sẽ thấy trạng thái là “inactive (dead)”. Điều này xác nhận rằng không còn tiến trình nào đang truy cập vào thư mục dữ liệu cũ, và chúng ta có thể an toàn sao chép chúng.
Di chuyển dữ liệu sang thư mục mới
Bây giờ là lúc chuyển toàn bộ dữ liệu từ thư mục cũ sang thư mục mới đã chuẩn bị. Chúng ta nên sử dụng lệnh rsync thay vì cp. Lệnh rsync có nhiều ưu điểm, đặc biệt là tùy chọn -a (archive mode), giúp sao chép đệ quy, bảo toàn symlinks, quyền sở hữu, thời gian sửa đổi và các thuộc tính khác của file.
Giả sử phiên bản PostgreSQL của bạn là 12 và thư mục dữ liệu cũ là /var/lib/postgresql/12/main/. Lệnh di chuyển sẽ như sau:
sudo rsync -av /var/lib/postgresql/12/main/ /mnt/data/postgresql-data/

Lưu ý dấu gạch chéo / ở cuối đường dẫn nguồn. Nó đảm bảo rằng nội dung của thư mục main được sao chép vào postgresql-data, chứ không phải cả thư mục main lồng bên trong. Sau khi quá trình sao chép hoàn tất, bạn nên kiểm tra lại để xác nhận dữ liệu đã được chuyển đi chính xác. Bạn có thể so sánh kích thước của hai thư mục hoặc kiểm tra một vài file ngẫu nhiên.
Cấu hình PostgreSQL sử dụng thư mục dữ liệu mới
Dữ liệu đã ở vị trí mới, nhưng PostgreSQL vẫn chưa biết điều đó. Chúng ta cần cập nhật file cấu hình để chỉ cho nó đường dẫn mới. File cấu hình chính của PostgreSQL là postgresql.conf, thường nằm trong /etc/postgresql/<version>/main/. Để hiểu rõ hơn về hệ điều hành Ubuntu và cách quản lý các dịch vụ cũng như file cấu hình, bạn có thể tham khảo thêm bài viết Hệ điều hành Ubuntu là gì.
Mở file này bằng một trình soạn thảo văn bản như nano:
sudo nano /etc/postgresql/12/main/postgresql.conf
Tìm đến dòng có chứa tham số data_directory. Dòng này có thể đang bị comment (có dấu # ở đầu). Hãy bỏ comment và thay đổi giá trị của nó thành đường dẫn mới:
data_directory = '/mnt/data/postgresql-data'

Hãy chắc chắn rằng đường dẫn bạn nhập là chính xác tuyệt đối. Sau khi chỉnh sửa, lưu và đóng file lại. Đây là bước quan trọng nhất để hệ thống nhận diện được “ngôi nhà” mới của mình.
Khởi động lại dịch vụ và kiểm tra hoạt động
Mọi thứ đã được thiết lập. Bây giờ là lúc khởi động lại dịch vụ PostgreSQL và xem kết quả.
Sử dụng lệnh systemctl để khởi động dịch vụ:
sudo systemctl start postgresql
Ngay sau khi khởi động, hãy kiểm tra lại trạng thái của nó:
sudo systemctl status postgresql
Nếu trạng thái là “active (running)”, xin chúc mừng, bạn đã di chuyển thành công! Tuy nhiên, đừng vội mừng. Bước cuối cùng là kiểm tra kết nối đến cơ sở dữ liệu và xem các file log để đảm bảo không có lỗi ngầm nào xảy ra.
Bạn có thể kết nối thử bằng psql:
sudo -u postgres psql
Nếu bạn có thể kết nối và thực hiện truy vấn, quá trình đã hoàn tất. Đồng thời, hãy kiểm tra file log của PostgreSQL, thường nằm ở /var/log/postgresql/postgresql-<version>-main.log, để tìm kiếm bất kỳ cảnh báo hoặc lỗi nào. Để nắm rõ hơn về hệ thống kernel Linux và liên quan đến hiệu suất hệ điều hành, bạn có thể tham khảo bài viết Kernel Linux.
Các lưu ý và xử lý sự cố thường gặp
Mặc dù quy trình trên khá đơn giản, nhưng đôi khi vẫn có thể xảy ra sự cố. Việc hiểu rõ các vấn đề thường gặp và cách khắc phục sẽ giúp bạn tự tin hơn khi thực hiện.
PostgreSQL không khởi động sau khi thay đổi thư mục dữ liệu
Đây là lỗi phổ biến nhất. Nếu dịch vụ PostgreSQL không thể khởi động sau khi bạn đã thay đổi cấu hình, nguyên nhân hàng đầu thường liên quan đến quyền truy cập thư mục. Hãy kiểm tra lại hai điều:
- Quyền sở hữu: Thư mục dữ liệu mới (
/mnt/data/postgresql-data) và tất cả các file bên trong có thực sự thuộc sở hữu của người dùngpostgreskhông? Chạy lại lệnhsudo chown -R postgres:postgres /mnt/data/postgresql-datađể chắc chắn. Tùy chọn-Rsẽ áp dụng quyền cho tất cả các file và thư mục con. - Quyền truy cập: Thư mục dữ liệu chính có quyền
0700không? Chạy lệnhsudo chmod 700 /mnt/data/postgresql-datađể đảm bảo chỉ người dùngpostgresmới có quyền truy cập.

Một nguyên nhân khác có thể là do bạn đã sao chép thiếu file hoặc dữ liệu bị hỏng trong quá trình di chuyển. Hãy thử so sánh kích thước hoặc số lượng file giữa thư mục cũ và mới. Nếu có sự khác biệt, bạn nên dừng dịch vụ và thực hiện lại quá trình rsync.
Lỗi phân quyền dẫn đến không truy cập cơ sở dữ liệu được
Trong một số trường hợp, dịch vụ có thể khởi động nhưng bạn lại không thể kết nối đến cơ sở dữ liệu. Lỗi này thường cũng xuất phát từ vấn đề phân quyền, nhưng có thể ở mức độ chi tiết hơn bên trong thư mục dữ liệu.
Hãy kiểm tra lại quyền sở hữu và quyền truy cập của toàn bộ cây thư mục. Sử dụng lệnh ls -lR /mnt/data/postgresql-data để xem chi tiết. Mọi file và thư mục bên trong đều phải thuộc sở hữu của postgres. Nếu bạn phát hiện bất kỳ file nào có chủ sở hữu khác (ví dụ như root), đó chính là vấn đề. Lệnh sudo chown -R postgres:postgres /mnt/data/postgresql-data sẽ khắc phục được điều này.
Ngoài ra, một số hệ thống Linux có các cơ chế bảo mật nâng cao như AppArmor hoặc SELinux. Các cơ chế này có thể ngăn PostgreSQL truy cập vào một đường dẫn không chuẩn. Bạn cần kiểm tra log hệ thống (journalctl -u postgresql) để xem có thông báo lỗi nào liên quan đến “permission denied” từ AppArmor hay không. Nếu có, bạn sẽ cần phải cập nhật lại cấu hình của AppArmor để cho phép PostgreSQL truy cập vào thư mục mới.
Các thực hành tốt nhất khi di chuyển thư mục dữ liệu PostgreSQL
Để đảm bảo quá trình di chuyển dữ liệu diễn ra an toàn, hiệu quả và giảm thiểu rủi ro, bạn nên tuân thủ một số nguyên tắc và thực hành tốt nhất sau đây.
- Luôn sao lưu dữ liệu trước khi thực hiện: Đây là quy tắc vàng. Trước khi thực hiện bất kỳ thay đổi lớn nào đối với cơ sở dữ liệu, hãy tạo một bản sao lưu đầy đủ. Nếu có sự cố không mong muốn xảy ra, bạn vẫn có thể khôi phục lại trạng thái ban đầu một cách nhanh chóng. Sử dụng
pg_dumpallhoặc các công cụ sao lưu chuyên dụng khác. - Sử dụng lệnh
rsyncđể bảo toàn quyền và phân quyền file: Như đã đề cập,rsync -avlà công cụ lý tưởng cho việc này. Nó không chỉ sao chép dữ liệu mà còn đảm bảo rằng các thuộc tính quan trọng như quyền sở hữu, quyền truy cập và symlinks được giữ nguyên. Điều này giúp tránh được rất nhiều lỗi tiềm ẩn liên quan đến phân quyền. - Không thay đổi thư mục dữ liệu khi PostgreSQL đang chạy: Việc này có thể dẫn đến hỏng dữ liệu (data corruption) không thể phục hồi. Luôn đảm bảo dịch vụ đã được dừng hoàn toàn (
systemctl stop postgresql) và kiểm tra trạng thái (systemctl status postgresql) trước khi bắt đầu sao chép. - Theo dõi logs kỹ càng sau khi chuyển đổi: Sau khi khởi động lại dịch vụ, đừng cho rằng mọi thứ đã ổn chỉ vì nó báo “active”. Hãy dành thời gian kiểm tra file log của PostgreSQL và log hệ thống. Các cảnh báo hoặc lỗi nhỏ có thể là dấu hiệu của những vấn đề lớn hơn trong tương lai. Việc phát hiện sớm sẽ giúp bạn xử lý kịp thời.
- Cân nhắc đổi tên thư mục cũ: Sau khi đã xác nhận hệ thống hoạt động ổn định với thư mục dữ liệu mới, bạn có thể đổi tên thư mục dữ liệu cũ (ví dụ:
main_old) thay vì xóa ngay lập tức. Điều này cho phép bạn có một phương án dự phòng nhanh chóng trong trường hợp cần quay lại cấu hình cũ. Sau một vài ngày hoặc vài tuần hoạt động ổn định, bạn có thể xóa thư mục cũ để giải phóng dung lượng.

Kết luận
Việc di chuyển thư mục dữ liệu PostgreSQL trên Ubuntu 20.04 là một tác vụ quản trị hệ thống quan trọng, giúp tối ưu hóa hiệu suất, đơn giản hóa việc quản lý dung lượng và tăng cường bảo mật. Mặc dù quá trình này đòi hỏi sự cẩn thận, nhưng bằng cách tuân theo các bước đã được trình bày chi tiết – từ chuẩn bị thư mục mới, dừng dịch vụ, di chuyển dữ liệu bằng rsync, cập nhật file cấu hình, cho đến khởi động và kiểm tra lại – bạn hoàn toàn có thể thực hiện thành công.
Điều cốt lõi nằm ở khâu chuẩn bị kỹ càng, đặc biệt là việc thiết lập đúng quyền sở hữu và quyền truy cập cho thư mục mới. Luôn nhớ sao lưu dữ liệu trước khi bắt đầu và kiểm tra log hệ thống cẩn thận sau khi hoàn tất để đảm bảo mọi thứ hoạt động như mong đợi. Hy vọng rằng hướng dẫn này từ AZWEB sẽ giúp bạn quản lý hệ thống cơ sở dữ liệu PostgreSQL của mình một cách chuyên nghiệp và hiệu quả hơn. Để tối ưu hơn nữa, bạn có thể tham khảo thêm tài liệu chính thức của PostgreSQL và các bài viết chuyên sâu về tinh chỉnh hiệu suất trên Ubuntu.