1. 要件
- コンテナ (docker) でDBが構築されている
- PostgreSQL(image)のversionが最新になっている
- vector型が使える (vector拡張がインストールされている)
- retriever用のDB/USER/Access Controlがセットアップされている
2. 検討
- officialを見ると17.4が最新になっており、pgvector拡張を見ると拡張追加の方法が明示されてるので、docker-composeに
build
entryを書いて構築する (1, 2, 3)。 restart
entryは、unless-stopped
だと手動でcontainerをstopし、そのまま忘れてシステム再起動した時に自動で立ち上がらないのでrestart: always
とする。- 検討すべきはretriever向けのAccess Controlだが、retriever用以外はlocal向け用途なのでネットワークレベルで制御する (4)。
- 他は一般的な制御をする (できるだけ最小の権限を付与)。
3. 作業
掃除
既存のcontainer/imageの削除や、dataファイルの退避 (予めbackupは取っておく)を行う。
psql --version
docker container rm pg
docker image rm postgres
sudo mv db_data/pg/ /tmp/
Dockerfile (pg-dockerfile) の作成
# Dockerfile
FROM postgres:17.4
RUN apt-get update && \
apt-get install -y git make gcc postgresql-server-dev-17
RUN cd /tmp && \
git clone --branch v0.8.0 https://github.com/pgvector/pgvector.git && \
cd pgvector && \
make && \
make install && \
cd ../ && rm -rf pgvector
docker-compose.ymlの更新
build
entryを追加し、build後のimage名はvectorを冠するものにしたいのでそうする。
build:
context: .
dockerfile: ./dockerfiles/pg-dockerfile
image: pg17-vector-enabled
build & up
対応するimageが存在しないので、以下のコマンドで build
と up
(i.e. running daemon) が実行される。
docker-compose up pg
- 立ち上がりのログが見たいのでこうするが、無事立ち上がるとterminalを占有するので
Ctrl-C-C
で落とし、改めてdocker-compose start
でdaemonizeする。 - 最初からdaemonizeしたいなら
--detach
を付ける等あったと思う(お薦めしない)。 llvm
libraryのインストールに時間がかかった(2~3分程)ので、フリーズしたかと思って調べた。
CREATE ROLE
- PostgreSQLにおいてROLEはUSERのsynonymになっており、ユーザの設定を変える際、
ALTER USER
ではなくALTER ROLE
とする。 - CREATE DATABASEの
TEMPLATE template1
は公式を見ると不要と分かる (defaultでtemplate1のコピーを作る為)。 - SCHEMAはDATABASE下の「ディレクトリ」に相当するので、DATABASEに接続し直す必要がある。
- 論理的な境界線を規定するもので、例えばSELECTでそれ以下のどのTABLEが見える(指定できる)かが決まる (c.f.
role
やsession
ごとに指定できるsearch_path
で設定) - SCHEMAへのGRANTは、公式にあるように
USAGE
,CREATE
,ALL
のみ指定可能。 - PRIVILEGES節を見ると,
USAGE
は参照、CREATE
は(TABLE等も含むDATABASE OBJECTの)作成
- 論理的な境界線を規定するもので、例えばSELECTでそれ以下のどのTABLEが見える(指定できる)かが決まる (c.f.
CREATE USER some_retriever WITH PASSWORD '******';
CREATE DATABASE vector_db TEMPLATE template1;
GRANT ALL PRIVILEGES ON DATABASE vector_db TO some_retriever ;
\c vector_db postgres
# connected to database "vector_db" as user "postgres".
GRANT ALL ON SCHEMA public TO some_retriever ;
vector拡張の有効化
拡張有効化はDATABASEごとに行うことができ、有効化にはsuper user権限が必要。
\c vector_db
CREATE EXTENSION vector;
vector拡張の有効化確認
\dx
List of installed extensions
Name | Version | Schema | Description
---------+---------+------------+------------------------------------------------------
plpgsql | 1.0 | pg_catalog | PL/pgSQL procedural language
vector | 0.8.0 | public | vector data type and ivfflat and hnsw access methods
Vectorizeされたdocumentの確認と照合
適当なdocument (c.f. 画像はこのブログの記事のchunk) を準備し、
- Simple (On Memory / File storage)
- Vector DB
二つの方法 (i.e. store
) でindexを保存した (c.f. 例ではindexingにllamaindexを使用)。


- 左はSimpleで永続化して出力されるファイルの一つで
docstore.json
というファイル。 - 右は先に準備したDATABASE (i.e.
vector_db.metadata_
)に保存されたdocumentのmetaデータ。 - それぞれ異なるタイミング・方法で永続化しても整合している事が分かる。
- llamaindexの場合、DATABASEだけ作ればTABLEはパラメタから導出されて自動で作られる。
4. まとめ
今回はvector拡張付きのPostgreSQLを構築し、データが入る所までを確認した。
仕事で余り使う機会がないPostgreSQLは、個人的に一番好きなRDBMS (実際、個人のプロジェクトはSQLiteかPostgreSQLを使う)。