{"id":445,"date":"2019-02-21T11:51:57","date_gmt":"2019-02-21T02:51:57","guid":{"rendered":"http:\/\/localhost:8000\/?p=445"},"modified":"2021-01-23T11:53:53","modified_gmt":"2021-01-23T02:53:53","slug":"postgresql-tips","status":"publish","type":"post","link":"http:\/\/localhost:8000\/2019\/02\/postgresql-tips.html","title":{"rendered":"PostgreSQL\u306eTips"},"content":{"rendered":"

PostgreSQL\u306b\u95a2\u3059\u308bTips\u3092\u30e1\u30e2\u3002<\/p>\n

DB\u4f5c\u6210\u3001\u30e6\u30fc\u30b6\u4f5c\u6210\u3001\u30c7\u30d5\u30a9\u30eb\u30c8\u6a29\u9650\u4ed8\u4e0e\u3001\u30b9\u30ad\u30fc\u30de\u3078\u306e\u6a29\u9650\u4ed8\u4e0e<\/h2>\n

dba\u30e6\u30fc\u30b6\u3068app\u30e6\u30fc\u30b6\u3092\u4f5c\u3063\u3066\u3001app\u30e6\u30fc\u30b6\u306b\u30c7\u30d5\u30a9\u30eb\u30c8\u6a29\u9650\u3092\u8a2d\u5b9a\u3059\u308b\u3002
\n\u8a73\u7d30\u306f\u3053\u3061\u3089<\/a>\u3092\u53c2\u7167\u306e\u3053\u3068\u3002<\/p>\n

psql -U postgres\n=> -- \u30e6\u30fc\u30b6\u4f5c\u6210\n=> create user hoge_dba password 'hoge_dba';\n=> create user hoge_app password 'hoge_app';\n=> -- DB\u4f5c\u6210\n=> create database hoge owner hoge_dba;\n=> -- \u30c7\u30d5\u30a9\u30eb\u30c8\u6a29\u9650\u4ed8\u4e0e\n=> alter default privileges in schema public grant all on tables to hoge_app;\n=> alter default privileges in schema public grant all on sequences to hoge_app;\n=> alter default privileges in schema public grant all on functions to hoge_app;\n=> -- \u30b9\u30ad\u30fc\u30de\u3078\u306e\u6a29\u9650\u4ed8\u4e0e\n=> grant all on schema public to hoge_app; -- \u30b9\u30ad\u30fc\u30de\u3078\u306e\u6a29\u9650\u304c\u306a\u3044\u3068\u305d\u3082\u305d\u3082\u305d\u306e\u30b9\u30ad\u30fc\u30de\u306a\u3044\u306e\u30aa\u30d6\u30b8\u30a7\u30af\u30c8\u304c\u898b\u3048\u306a\u3044\n=> grant select on all tables in schema public to hoge_app; -- \u65e2\u5b58\u30c6\u30fc\u30d6\u30eb\u3078\u306e\u30a2\u30af\u30bb\u30b9\u6a29\u9650<\/code><\/pre>\n

seq scan\u3084index scan\u306e\u56de\u6570\u3001\u30d5\u30a7\u30c3\u30c1\u6570\u7b49\u3092\u78ba\u8a8d<\/h2>\n
select * from pg_stat_user_tables<\/code><\/pre>\n

\u30ed\u30c3\u30af\u4e2d\u306e\u30d7\u30ed\u30bb\u30b9\u3092\u53d6\u5f97<\/h2>\n
select\n  l.pid\n  , db.datname\n  , c.relname\n  , l.locktype\n  , l.mode\nfrom\n  pg_locks l\n  left join pg_class c on (l.relation=c.relfilenode)\n  left join pg_database db on (l.database = db.oid ORDER BY l.pid)<\/code><\/pre>\n

\u30d7\u30ed\u30bb\u30b9\u3092kill\u3059\u308b\uff08super user\u306e\u307f\uff09<\/h2>\n
select pg_terminate_backend(${pid});<\/code><\/pre>\n

\u5b9f\u884c\u4e2dSQL\u3092\u63a2\u3059<\/h2>\n

full SQL\u304c\u898b\u305f\u3044\u5834\u5408\u306fsrc\/include\/pgstat.h<\/code>\u306e PGSTAT_ACTIVITY_SIZE\u3092\u5909\u66f4\u3059\u308b\u3089\u3057\u3044<\/p>\n

select\n  procpid\n  , start\n  , now() - start as lap\n  , current_query \nfrom\n  (\n  select\n    backendid\n    , pg_stat_get_backend_pid(s.backendid) as procpid\n    , pg_stat_get_backend_activity_start(s.backendid) as start\n    , pg_stat_get_backend_activity(s.backendid) as current_query \n  from\n    (select pg_stat_get_backend_idset() as backendid) as s\n  ) as s \nwhere\n  current_query <> '<IDLE>'\norder by\n  start<\/code><\/pre>\n

\u6700\u5f8c\u306bAnalyze\u3057\u305f\u65e5\u6642\u3092\u78ba\u8a8d<\/h2>\n
select\n  relname, n_live_tup, n_dead_tup, last_vacuum, last_autovacuum, last_analyze, last_autoanalyze, schemaname\nfrom\n  pg_stat_all_tables\nwhere\n  schemaname = 'hoge'\norder by\n  relname;<\/code><\/pre>\n

\u30a4\u30f3\u30c7\u30c3\u30af\u30b9\u306e\u5bb9\u91cf\u78ba\u8a8d<\/h2>\n
select\n  *, pg_size_pretty(pg_relation_size(indexrelid))\nfrom\n  pg_stat_user_indexes\nwhere\n  idx_scan = 0\n  and idx_tup_read = 0\n  and idx_tup_fetch = 0\norder by\n  pg_size_pretty desc<\/code><\/pre>\n

\u30ec\u30b3\u30fc\u30c9\u30ed\u30c3\u30af\u305b\u305aindex\u4f5c\u6210<\/h2>\n
create index concurrently<\/code><\/pre>\n

\u73fe\u5728\u306e\u30b7\u30fc\u30b1\u30f3\u30b9\u756a\u53f7\u78ba\u8a8d<\/h2>\n
select last_value from hoge_seq<\/code><\/pre>\n

\u30b7\u30fc\u30b1\u30f3\u30b9\u756a\u53f7\u3092\u30ea\u30bb\u30c3\u30c8\u3059\u308b<\/h2>\n
alter sequence hoge_seq restart with \u6b21\u306b\u53d6\u5f97\u3057\u305f\u3044\u756a\u53f7<\/code><\/pre>\n

\u518d\u8d77SQL\u306e\u30b5\u30f3\u30d7\u30eb<\/h2>\n

2016\/06\/01\u304b\u3089\u73fe\u5728\u307e\u3067\u306e7\u65e5\u6bce\u306e\u65e5\u4ed8\u30ea\u30b9\u30c8\u3092\u751f\u6210<\/p>\n

with recursive tmp(day) as (\n  values (to_timestamp('201606', 'YYYYMM'))\n  -- \u2191\u306f select to_timestamp('201606', 'YYYYMM') \u3068\u540c\u7fa9\n  union all\n  select\n    day + '7days'\n  from\n    tmp\n  where\n    day + '5days' <= current_timestamp\n)\nselect * from tmp;<\/code><\/pre>\n

\u6587\u5b57\u5217\u3092split\u3057\u3066\u30c6\u30fc\u30d6\u30eb\u3084\u914d\u5217\u306b\u5c55\u958b\u3059\u308b<\/h2>\n
-- \u30c6\u30fc\u30d6\u30eb\u3078\u5c55\u958b\nselect regexp_split_to_table('aaa,bbb,ccc', ',');\n> "aaa"\n> "bbb"\n> "ccc"\n\n-- \u914d\u5217\u3078\u5c55\u958b\nselect regexp_split_to_array('aaa,bbb,ccc', ',');\n> "{aaa,bbb,ccc}"<\/code><\/pre>\n

json\u914d\u5217\u3092\u30c6\u30fc\u30d6\u30eb\u306b\u5c55\u958b\u3059\u308b<\/h2>\n

lateral\u3092\u3064\u3051\u308b\u3068\u305d\u306e\u95a2\u6570\u3084\u30b5\u30d6\u30af\u30a8\u30ea\u304c\u3001\u540c\u5217\u306e\u95a2\u6570\u3084\u30b5\u30d6\u30af\u30a8\u30ea\u3088\u308a\u3082\u3042\u3068\u306b\u5b9f\u884c\u3055\u308c\u308b\u306e\u3067\u3001\u4ed6\u306e\u30b5\u30d6\u30af\u30a8\u30ea\u306e\u7d50\u679c\u3092\u3064\u304b\u3048\u308b\u3088\u3046\u306b\u306a\u308b<\/p>\n

with fuga_table as (\nselect\n  h.id\n  , h.name\n  , cast(value->'def_id' as text) as def_id\n  , cast(value->'def_name' as text) as def_name\n  , cast(value->'def_type' as text) as def_type\nfrom\n  hoge h,\n  lateral json_array_elements(h.fuga_json::json)\nwhere\n  h.id < 1000\n)\nselect\n  *\nfrom\n  fuga_table\nwhere\n  def_type = '"text"'<\/code><\/pre>\n

\u30c0\u30f3\u30d7 & \u30ea\u30b9\u30c8\u30a2<\/h2>\n
## dump\n# connection_option -> option\u306e\u9806\u756a\n# -F: \u30d5\u30a9\u30fc\u30de\u30c3\u30c8\u6307\u5b9a p: plain\u306aSQL, c: \u30ab\u30b9\u30bf\u30e0\u30a2\u30fc\u30ab\u30a4\u30d6\uff08\u30d0\u30a4\u30ca\u30ea\u3002\u30b5\u30a4\u30ba\u304c\u5c0f\u3055\u3044\uff09\n# -t: \u5bfe\u8c61\u30c6\u30fc\u30d6\u30eb\u3092\u6307\u5b9a\n# -s: DDL\u3060\u3051\u51fa\u529b\n# -a: \u30c7\u30fc\u30bf\u306e\u307f\u51fa\u529b\n# --column-inserts \u30ab\u30e9\u30e0\u540d\u4ed8\u304dinsert\u6587\npg_dump -h {host} -p {port} -U {user} -d {db} -t {table_name} -Fc -f hoge.dmp\n\n## restore\n# connection_option -> option\u306e\u9806\u756a\n# option\u306e\u5185\u5bb9\u306fpg_dump\u3068\u307b\u307c\u540c\u3058\npg_restore -h {host} -p {port} -U {user} -d {db} -t {table_name} -Fc hoge.dmp\n<\/code><\/pre>\n

CSV\u30a8\u30af\u30b9\u30dd\u30fc\u30c8 & CSV\u30a4\u30f3\u30dd\u30fc\u30c8<\/h2>\n

psql\u306ecopy\u30b3\u30de\u30f3\u30c9\u3092\u5229\u7528\u3059\u308b\u65b9\u6cd5\u3092\u8a18\u8f09\u3059\u308b<\/p>\n

## CSV\u30a8\u30af\u30b9\u30dd\u30fc\u30c8\npsql -h {host} -p {port} -U {user} -d {db}\n=> \\copy {table_name} to '{csv_path}' with csv delimiter ','\n\n## CSV\u30a4\u30f3\u30dd\u30a4\u30fc\u30c8\npsql -h {host} -p {port} -U {user} -d {db}\n=> \\copy {table_name} (column_names,...) from '{csv_path}' with csv\n<\/code><\/pre>\n

\u30c7\u30fc\u30bf\u30d5\u30a9\u30eb\u30c0\u30d1\u30b9\u306e\u78ba\u8a8d<\/h2>\n
ps aux | grep postgres\n-> -D\u306e\u5f8c\u308d\u304c\u30c7\u30fc\u30bf\u30d5\u30a9\u30eb\u30c0<\/code><\/pre>\n

pg_hba.conf\u306e\u53cd\u6620<\/h2>\n
## \u8a2d\u5b9a\u30d5\u30a1\u30a4\u30eb\u3092\u518d\u8aad\u307f\u8fbc\u307f\u3059\u308b\npg_ctl reload -D {\u30c7\u30fc\u30bf\u30d5\u30a9\u30eb\u30c0\u30d1\u30b9}\n\n## postgresql\u81ea\u4f53\u3092\u518d\u8d77\u52d5\u3059\u308b\uff08service\u30b3\u30de\u30f3\u30c9\u3067\u8d77\u52d5\u3057\u3066\u3044\u308b\u5834\u5408\uff09\nservice postgresql restart<\/code><\/pre>\n

\u30b9\u30ad\u30fc\u30de\u691c\u7d22\u30d1\u30b9\uff08search_path\uff09\u306e\u8a2d\u5b9a<\/h2>\n

\u30b9\u30ad\u30fc\u30de\u540d.\u30aa\u30d6\u30b8\u30a7\u30af\u30c8\u540d<\/code>\u3067\u5b8c\u5168\u4fee\u98fe\u3059\u308b\u3053\u3068\u3082\u3067\u304d\u307e\u3059\u304c\u3001\u30b9\u30ad\u30fc\u30de\u540d\u3067\u8a18\u8f09\u3057\u306a\u3044\u5834\u5408\u3001\u30b9\u30ad\u30fc\u30de\u691c\u7d22\u30d1\u30b9\u306b\u6307\u5b9a\u3055\u308c\u3066\u308b\u30b9\u30ad\u30fc\u30de\u3092\u9806\u756a\u306b\u53c2\u7167\u3057\u307e\u3059\u3002
\n\u5e38\u306b\u30b9\u30ad\u30fc\u30de\u540d\u3067\u4fee\u98fe\u3059\u308b\u306e\u306f\u5927\u5909\u306a\u306e\u3067\u3001\u30b9\u30ad\u30fc\u30de\u691c\u7d22\u30d1\u30b9\u3092\u8a2d\u5b9a\u3059\u308b\u65b9\u6cd5\u3092\u8a18\u8f09\u3057\u307e\u3059\u3002<\/p>\n

psql -h {host} -p {port} -U {user} -d {db}\n=> -- search_path\u3092\u78ba\u8a8d\u3059\u308b\n=> show search_path;\n   search_path   \n-----------------\n "$user", public\n(1 row)\n=> -- \u30bb\u30c3\u30b7\u30e7\u30f3\u5185\u3067search_path\u3092\u8a2d\u5b9a\u3059\u308b\n=> set search_path = "hoge", "$user", public;\nSET\n=> -- \u30e6\u30fc\u30b6\u306esearch_path\u3092\u8a2d\u5b9a\u3059\u308b\n=> alter user {user} set search_path to "hoge", "$user", public;\nALTER ROLE<\/code><\/pre>\n","protected":false},"excerpt":{"rendered":"

PostgreSQL\u306b\u95a2\u3059\u308bTips\u3092\u30e1\u30e2\u3002 DB\u4f5c\u6210\u3001\u30e6\u30fc\u30b6\u4f5c\u6210\u3001\u30c7\u30d5\u30a9\u30eb\u30c8\u6a29\u9650\u4ed8\u4e0e\u3001\u30b9\u30ad\u30fc\u30de\u3078\u306e\u6a29\u9650\u4ed8\u4e0e dba\u30e6\u30fc\u30b6\u3068app\u30e6\u30fc\u30b6\u3092\u4f5c\u3063\u3066\u3001app\u30e6\u30fc\u30b6\u306b\u30c7\u30d5\u30a9\u30eb\u30c8\u6a29\u9650\u3092\u8a2d\u5b9a\u3059\u308b\u3002 \u8a73\u7d30\u306f\u3053\u3061\u3089\u3092\u53c2\u7167\u306e\u3053\u3068\u3002 psql -U postgres => — \u30e6\u30fc\u30b6\u4f5c\u6210 => create user hoge_dba password 'hoge_dba'; => create user hoge_app password 'hoge_app'; => — DB\u4f5c\u6210 => create database hoge owner hoge_dba; => — \u30c7\u30d5\u30a9\u30eb\u30c8\u6a29\u9650\u4ed8\u4e0e => alter default privileges in schema public grant all on tables <\/span>Continue Reading<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"comment_status":"closed","ping_status":"open","sticky":false,"template":"","format":"standard","meta":[],"categories":[34],"tags":[],"_links":{"self":[{"href":"http:\/\/localhost:8000\/wp-json\/wp\/v2\/posts\/445"}],"collection":[{"href":"http:\/\/localhost:8000\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"http:\/\/localhost:8000\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"http:\/\/localhost:8000\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"http:\/\/localhost:8000\/wp-json\/wp\/v2\/comments?post=445"}],"version-history":[{"count":1,"href":"http:\/\/localhost:8000\/wp-json\/wp\/v2\/posts\/445\/revisions"}],"predecessor-version":[{"id":446,"href":"http:\/\/localhost:8000\/wp-json\/wp\/v2\/posts\/445\/revisions\/446"}],"wp:attachment":[{"href":"http:\/\/localhost:8000\/wp-json\/wp\/v2\/media?parent=445"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"http:\/\/localhost:8000\/wp-json\/wp\/v2\/categories?post=445"},{"taxonomy":"post_tag","embeddable":true,"href":"http:\/\/localhost:8000\/wp-json\/wp\/v2\/tags?post=445"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}