Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Loading...
Table of Contents 22.1. Overview 22.2. Creating a Database 22.3. Template Databases 22.4. Database Configuration 22.5. Destroying a Database 22.6. Tablespaces
正在執行的 PostgreSQL 伺服器的每個執行程序都會管理一個或多個資料庫。而資料庫是組織 SQL 物件(資料庫物件)的最高層級。本章介紹資料庫的屬性以及如何建立、管理和銷毀資料庫。
版本:11
CREATE DATABASE 實際上是透過複製現有資料庫來作業的。預設情況下,它是複製名為 template1 的標準系統資料庫。因此,該資料庫是製作新資料庫的「樣板」。如果向 template1 新增物件,則會使這些物件複製到隨後建立的使用者資料庫中。此行為可以對資料庫中的標準物件集合進行本地的修改。例如,如果在 template1 中安裝程序語言 PL/Perl,它將自動在使用者資料庫中可用,而在建立這些資料庫時不需要採取任何額外操作。
有一個名為 template0 的第二個標準系統資料庫。此資料庫包含與 template1 初始內容相同的資料,即只有您的 PostgreSQL 版本預先定義的標準物件。初始化資料庫叢集後,永遠都不應變更 template0。透過指示 CREATE DATABASE 複製 template0 而不是 template1,您可以建立一個「virgin」使用者資料庫,其中不包含 template1 中的任何本地變更。這在恢復 pg_dump 轉存時尤其方便:轉存腳本應該在原始資料庫中恢復,以確保重新建立轉存資料庫的正確內容,而不會與稍後可能增加到 template1 的物件發生衝突。
複製 template0 而不是 template1 的另一個常見原因是,在複製 template0 時可以指定新的編碼和區域設定,而 template1 的副本必須使用與其相同的設定。這是因為 template1 可能包含特定於編碼或特定於語言環境的資料,是 template0 所不知道的。
要透過複製 template0 建立資料庫,請使用:
在 SQL 環境,或:
在命令列。
要建立其他樣模資料庫,實際上可以透過將其名稱指定為 CREATE DATABASE 的樣板來複製叢集中的任何資料庫。然而,重要的是要理解,這不能用作通用的「COPY DATABASE」操作。主要限制是在複製來源資料庫時不能將其他連線連接到來源資料庫。如果啟動時存在任何其他的連線,則 CREATE DATABASE 將會失敗;在複製操作期間,會阻止與來源資料庫的新連線。
每個資料庫的 pg_database 中都存在兩個有用的標記:欄位 datistemplate 和 datallowconn。可以設定 datistemplate 以指示資料庫是否用作 CREATE DATABASE 的樣板。如果設定了此標記,則任何具有 CREATEDB 權限的使用者都可以複製資料庫;如果未設定,則只有超級使用者和資料庫的所有者才能複製它。如果 datallowconn 為 false,則不允許與該資料庫建立新的連線(但僅透過將標記設定為 false,不會終止現有連線)。template0 資料庫通常標記為 datallowconn = false 以防止其修改。template0 和 template1 都應該始終保持 datistemplate = true 標記。
除了名稱 template1 是 CREATE DATABASE 的預設來源資料庫名稱之外,template1 和 template0 沒有任何特殊狀態。例如,可以刪除 template1 並從 template0 重新建立它而不會產生任何不良影響。如果一個人在 template1 中不小心加入了一堆垃圾,那麼這個方案可能是可接受的。(要刪除 template1,必須具有 pg_database.datistemplate = false。)
初始化資料庫叢集時也會建立 postgres 資料庫。此資料庫用作連線使用者和應用程序的預設資料庫。它只是 template1 的副本,可以在必要時刪除並重新建立。
PostgreSQL 中的資料表空間允許資料庫管理者定義檔案系統中可以儲存資料庫物件的檔案的路徑。建立完成後,在建立資料庫物件時可以透過名稱來引用資料表空間。
通過使用資料表空間,管理者可以控制 PostgreSQL 安裝的磁碟規畫。至少在兩個方面是很有用的。首先,如果初始化叢集的分割區(partition)或磁碟區(volume)的空間不足並且無法擴展時,則可以在不同的分割區上建立資料表空間,資料庫系統重新配置即可使用。
其次,資料表空間允許管理者依資料庫物件特性的知識來優化效能。例如,使用率很高的索引可以放置在非常快速、高可用的磁碟上,例如昂貴的固態磁碟。另一方面,對於很少使用或不關鍵的歸檔資料的資料表可以儲存在較便宜、速度較慢的磁碟系統上。
即使位於主 PostgreSQL 資料目錄之外,資料表空間也是資料庫叢集組成的一部分,並且它將作為資料檔案的自治集合來處理。它們會依賴於主資料目錄中包含的中繼資料,因此無法附加到不同的資料庫叢集或單獨備份。同樣,如果您失去了一個資料表空間(檔案被刪除、磁碟故障等),資料庫叢集可能變得不可讀取或無法啟動。所以將資料表空間放置在臨時檔案系統(如 RAM Disk)上會影響整個叢集的可靠性。
要定義資料表空間,請使用 CREATE TABLESPACE 指令,例如:
該路徑必須是 PostgreSQL 作業系統使用者所擁有的空白目錄。隨後在資料表空間內建立的所有物件都將儲存在此目錄下的檔案中。該位置不得位於可移除或瞬時儲存上,因為如果資料表空間失去了,叢集可能會無法運行。
在每個邏輯檔案系統中建立多個資料表空間通常沒有什麼意義,因為你無法控制邏輯檔案系統內單個檔案的位置。但是,PostgreSQL 不會強制實施任何此類限制,事實上它並不直接發現系統上的檔案系統界線。 它只是將檔案儲存在你告訴它所使用的目錄中而已。
建立資料表空間本身必須以資料庫超級使用者的身份完成,但在此之後,你可以允許普通的資料庫使用者來使用它。為此,請為它們授予 CREATE 的權限。
資料表、索引和整個資料庫可以分配給特定的資料表空間。為此,具有給定資料表空間上的 CREATE 權限的使用者必須將資料表空間名稱作為參數傳遞給相關的指令。例如,下面會在資料表空間 space1 中建立一個資料表:
或者,使用 default_tablespace 參數:
當 default_tablespace 設定為空字符之外的任何內容時,它將為 CREATE TABLE 和 CREATE INDEX 指令提供一個隱含的 TABLESPACE 子句,當它們沒有明確的 TABLESPACE 子句的時候。
還有一個 temp_tablespaces 參數,用於指定臨時資料表和索引的位置,以及用於排序大型資料之類目的的臨時檔案。這可以是資料表空間名稱的列表,而不是只有一個,以便與臨時物件關聯的負載可以分佈在多個資料表空間中。每次建立臨時物件時都會挑選該列表的隨機成員。
與資料庫關聯的資料表空間用於儲存該資料庫的系統目錄。此外,如果沒有給予 TABLESPACE 子句也沒有其他由 default_tablespace 或 temp_tablespaces(根據需要)的選擇指定的話,那麼它是用於在資料庫內建立的資料表、索引和臨時檔案的預設資料表空間。如果建立的資料庫沒有為其指定資料表空間,則它使用與從其複製的模板資料庫相同的資料表空間。
當資料庫叢集初始化時,會自動建立兩個資料表空間。pg_global 資料表空間用於共享的系統目錄。pg_default 資料表空間是 template1 和 template0 資料庫的預設資料表空間(因此,除非它被 CREATE DATABASE 中的 TABLESPACE 子句所取代,否則它將成為其他資料庫的預設資料表空間)。
一旦建立之後,可以從任何資料庫使用資料表空間,只要請求的使用者具有足夠的權限即可。這意味著,除非所有使用資料表空間的資料庫中所有物件都被刪除,否則不能刪除資料表空間。
要刪除空的資料表空間,請使用 DROP TABLESPACE 指令。
例如,要確認一組現有的資料表空間,請檢查 pg_tablespace 系統目錄
psql 工具中的 \db 指令對於列出現有的資料表空間也很有用。
PostgreSQL 利用 symbolic link 來簡化資料表空間的管理。但這也意味著資料表空間只能用於支援 symbolic link 的系統。
目錄 $PGDATA/pg_tblspc 包含指向叢集中定義的每個非內建資料表空間的 symbolic link。儘管並不推薦,但可以透過重新定義這些連接來手動調整資料表空間的佈局。在伺服器運行期間,任何情況下都不會執行此操作。請注意,在 PostgreSQL 9.1 及更早版本中,你還需要使用新位置更新 pg_tablespace 目錄。(如果你不這樣做,pg_dump 將繼續輸出到舊的資料表空間路徑。)