16.3. 啟動資料庫伺服器

在任何人可以存取資料庫前,您必須啟動資料庫伺服器。 資料庫伺服器叫 postmasterpostmaster 必須知道到哪裡能找到她要用的資料。這是利用 -D 選項來實現的。 因此,啟動伺服器的最簡單的方法是,比如象下面這樣:

$ postmaster -D /usr/local/pgsql/data

這樣將把伺服器放在前台執行。這個步驟同樣必須以PostgreSQL 用戶帳戶登錄來做。沒有 -D 選項,伺服器將使用環境變量 PGDATA 命名的目錄; 如果這個環境變量也沒有,伺服器將失敗。

通常,最好在後台啟動 postmaster, 使用下面的 shell 語法:

$ postmaster -D /usr/local/pgsql/data > logfile 2>&1 &

把伺服器的stdoutstderr放到某個地方是非常重要的,就像在上面建議的這樣。 這樣做既可以幫助審計又可以幫助診斷問題。 (參閱 Section 21.3 獲取有關日誌文件處理的更完整的討論。)

postmaster 還接受一些其他的一些命令行選項。 更多的訊息請參考手冊頁 postmaster 和下面的 Section 16.4

這些 shell 語法很容易讓人覺得無聊。因此我們提供了封裝程序 pg_ctl 以簡化一些任務。比如,

pg_ctl start -l logfile

將在後台啟動伺服器並且把輸出放到指定的日誌文件中。 -D 選項和您直接執行postmaster時的意思是一樣的。 pg_ctl 還可以用於關閉伺服器。

通常,您會希望在計算機啟動的時候啟動資料庫伺服器。 自動啟動腳本是與操作系統相關的。 PostgreSQL 自己帶了幾個, 放在 contrib/start-scripts 目錄裡。 要想安裝其中一個,會需要 root 權限。

不同的系統在引導的時候有不同的啟動守護進程的方法,所以我們建議您先熟悉它們。 許多系統有名字稱為 /etc/rc.local/etc/rc.d/rc.local 這樣的文件, 其它的還有 rc.d 目錄。 不管您怎麼幹,都要記住伺服器必須以 PostgreSQL 用戶帳戶而不是以 root或者其他任何用戶的身份執行。 這樣,您可能總是要用下面這行的樣子構造您的命令: su -c '...' postgres。比如:

su -c 'pg_ctl -D /usr/local/pgsql/data -l serverlog' postgres

下面是一些比較詳細的與操作系統相關的建議。(每個例子裡我們使用具體數值的時候,都請注意把這些替換成合適的安裝路徑和用戶名。)

postmaster 執行的時候,它的PID是保存在資料目錄裡的文件 postmaster.pid 裡的。這樣做是為了避免多個postmaster在同一個資料目錄內執行,此文件同樣可以用於關閉postmaster

16.3.1. 伺服器啟動失敗

有幾個非常常見的原因會導致 postmaster 啟動失敗。 透過檢查 postmaster 日誌或者使用手工啟動的方法(不做 stdoutstderr 的重定向), 就可以看到錯誤訊息。下面我們更詳細地解釋了其中一些錯誤訊息。

LOG:  could not bind IPv4 socket: Address already in use
HINT:  Is another postmaster already running on port 5432? If not, wait a few seconds and retry.
FATAL:  could not create TCP/IP listen socket

就像它提示的那樣:您試圖在已經有一個 postmaster 執行著的連接埠上再執行了一個 postmaster。不過,如果內核的錯誤訊息不是 Address already in use 或者是其它的變種,那就有可能是別的毛病。 比如,試圖在一個保留的連接埠上執行postmaster會收到下面這樣的訊息:

$ postmaster -p 666
LOG:  could not bind IPv4 socket: Permission denied
HINT:  Is another postmaster already running on port 666? If not, wait a few seconds and retry.
FATAL:  could not create TCP/IP listen socket

像這樣的訊息

FATAL:  could not create shared memory segment: Invalid argument
DETAIL:  Failed system call was shmget(key=5440001, size=4011376640, 03600).

可能意味著您的內核對共享內存區的限制小於PostgreSQL 試圖分配的緩衝區大小(本例中是 4011376640 字元)。 或者可能意味著您根本就沒有配置System-V風格的共享內存支援。 作為一個臨時的解決辦法,您可以試著以小於正常數量的緩衝區數(-B開關)啟動伺服器。 您最終還是會希望重新配置您的內核,以增加共享內存的尺寸。如果您試圖在同一台機器上啟動多個伺服器, 而且她們所需的總空間超過了內核的限制,也會報這個錯。

象下面這樣的錯誤

FATAL:  could not create semaphores: No space left on device
DETAIL:  Failed system call was semget(5440126, 17, 03600).

意味著著您已經用光磁盤空間了。 它的意思是您的內核的System V信號燈的限制小於 PostgreSQL 想建立的數量。和上面一樣,您可以透過減少允許的連接數(-N開關)來繞開,但最終您還是會希望增加內核的限制。

如果您收到一個 "illegal system call" 錯誤,那麼很有可能是您的內核根本不支援共享內存或者信號燈。 如果是這樣的話,您的唯一選擇就是重新配置您的內核並且把這些特性打開。

關於配置系統System V IPC資源的細節見 Section 16.5.1

16.3.2. 客戶端連線問題

儘管可能在客戶端出現的錯誤條件範圍寬廣,而且還和應用相關,但的確有幾種錯誤與伺服器的啟動方式直接相關。 除了下面提到的幾種錯誤以外的問題都應該在相應的客戶端應用的文件中。

psql: could not connect to server: Connection refused
        Is the server running on host "server.joe.com" and accepting
        TCP/IP connections on port 5432?

這是純粹的 "我找不到可以交談的伺服器"錯誤。 當試圖進行 TCP/IP 通訊時它看起來像上面的樣子。 常見的錯誤是忘記把伺服器配置成允許 TCP/IP 連線。

另外,當試圖透過一個 Unix 套接字與本機伺服器通訊時,您會看到這個:

psql: could not connect to server: No such file or directory
        Is the server running locally and accepting
        connections on Unix domain socket "/tmp/.s.PGSQL.5432"?

最後一行可以有效地驗證客戶端進行連線嘗試時是否連對了位置。 如果實際上沒有伺服器在那裡執行,典型的內核錯誤是象上面顯示的那樣或者是 Connection refused 或者是 No such file or directory。 (尤其要注意的是這種環境下 Connection refused 的訊息顯示並意味著伺服器收到您的連線然後拒絕了連線。 那樣的話會產生一個不同的訊息,像 Section 19.3 裡面顯示的那樣) 其它像 Connection timed out 這樣的訊息資料表示更基本的問題,比如缺少網絡連線等。