Развертывание кластера Postgres-xl для чайников

Здравствуйте. Хочу поделиться с хабровчанами своим опытом развертывания кластера Postgres-xl в виде мини-инструкции для «чайников». Статей и мануалов на тему развертывания кластера postgres-xl не то чтобы много, но достаточно. И в них всех есть пару существенных недостатков на взгляд такого человека как я, который никогда прежде не занимался кластеризацией и тем более никогда прежде не работал в линукс-подобных осях. Все статьи подобного рода написаны для людей уже более-менее знакомых с линуксом и развертыванием postgresql/postgres-xl на таком окружении.

Поэтому и возникло желание поделится с остальными своими наработками. Далее я пошагово опишу весь процесс развертывания, от скачивания исходников postgres-xl и их компиляции, до конфигурирования кластера.

Так как много статей «для опытных» уже написано, и на хабре тоже, я опущу описание самого Postgres-xl, его компонентов и их типов (ролей).

Часть 1. Подготовка окружения


Для тестового кластера была выбрана конфигурация из 4 узлов: GTM, GTM-Standby и 2 нода (GTM-proxy, Coordinator, Datanode):

  • GTM1
    192.168.1.100
    GTM-Active: 6666

  • GTM2
    192.168.1.101
    GTM-Stanby: 6666

  • NODE1
    192.168.1.102
    GTM-Proxy1: 6666
    Coordinator1: 5432
    Datanode1: 15432

  • NODE2
    192.168.1.103
    GTM-Proxy2: 6666
    Coordinator2: 5432
    Datanode2: 15432

Все узлы являются виртуализированными машинами с 1024 Мб оперативной памяти и процессором с частотой 2.1Ghz. В выборе дистрибутива ОС я остановился на последней версии CentOS 7.0, его установку я тоже опущу. Устанавливал Minimal версию.

Часть 2. Установка зависимостей


Итак, у нас есть 4 чистых машины с установленным CentOS. Прежде чем приступить к скачке исходников из sourceforge установим для начала пакеты необходимые для компиляции самих исходников.

# yum install -y wget vim gcc make kernel-devel perl-ExtUtils-MakeMaker perl-ExtUtils-Embed readline-devel zlib-devel openssl-devel pam-devel libxml2-devel openldap-devel tcl-devel python-devel flex bison docbook-style-dsssl libxslt

Т.к. мы имеем чистую установку CentOS, то я добавил в этот шаг установку wget — менеджера загрузок и vim — текстового редактора. Также после установки пакетов не лишним будет обновить остальные пакеты командой:

# yum update -y 

Дождавшись окончания обновления, приступаем к следующей части процесса.

Часть 3. Загрузка исходного кода, его компиляция и установка


Для загрузки исходников выполняем команду:

# wget http://sourceforge.net/projects/postgres-xl/files/latest/download
# mv download pgxl-9.2.src.tar.gz

Или так:

# wget http://sourceforge.net/projects/postgres-xl/files/latest/download -O pgxl-9.2.src.tar.gz

Копируем скачанный архив в нужную папку и распаковываем:

# cp pgxl-9.2.src.tar.gz /usr/local/src/
# cd /usr/local/src/
# tar -xzvf pgxl-9.2.src.tar.gz

Архив распаковывается в папку postgres-xl, проверяем командой:

# ls

Для компиляции исходников и последующих установки и запуска нам нужна учетная запись не root пользователя, например:

# useradd postgres
# passwd postgres

Далее вводим и повторяем пароль, затем предоставляем права этому пользователю на всю папку с исходниками:

# chown -R postgres.postgres postgres-xl
# cd postgres-xl

Теперь нужно с помощью ./configure сконфигурировать исходники перед началом их компиляции, я использовал эту команду со следующими опциями:

# ./configure --with-tcl --with-perl --with-python --with-pam --with-ldap --with-openssl --with-libxml 

Подробнее об этих опциях можно почитать на странице официальной документации, тут.

Если вам не нужен какой либо модуль, то его можно не устанавливать на этапе установки зависимостей, либо использовать стандартную конфигурацию:

# ./configure

Для того чтобы скомпилированные исходники были переносимыми (чтобы не выполнять все предыдущие шаги на каждом из узлов кластера), нужно добавить ещё пару параметров --prefix и --disable-rpath. В итоге команда для установки с параметрами по умолчанию будет выглядеть так:

# ./configure --prefix=/usr/local/pgsql --disable-rpath

Параметр --prefix — это путь установки, он равен '/usr/local/pgsql' по умолчанию
Параметр --disable-rpath — этот параметр делает скомпилированные исходники переносимыми.

Теперь можно приступать непосредственно к самой компиляции, её нужно выполнять от имени пользователя который был создан ранее:

# su postgres
$ gmake world

либо

# su postgres -c 'gmake world'

Если компиляция прошла успешно, то последняя строчка в логе должна выглядеть так:

Postgres-XL, contrib and HTML documentation successfully made. Ready to install.


Всё! Всё скомпилировано, можно копировать папку /usr/local/src/postgres-xl на остальные узлы кластера и устанавливать.

Установка происходит по команде:

# gmake install-world

Повторяем данную команду на всех узлах кластера и приступаем к конфигурированию.

Часть 4. Конфигурирование


Для начала нужно произвести некоторые пост-инсталляционные настройки. Объявление environment переменных:

# echo 'export PGUSER=postgres' >> /etc/profile
# echo 'export PGHOME=/usr/local/pgsql' >> /etc/profile
# echo 'export PATH=$PATH:$PGHOME/bin' >> /etc/profile
# echo 'export LD_LIBRARY_PATH=$PGHOME/lib' >> /etc/profile

После чего надо перелогиниться. Логаут делаем командой:

# exit

Теперь приступаем к настройке узлов кластера. Для начала создаём папку с данными и инициализируем её в соответствии с ролью сервера.

GTM1/GTM2:

# mkdir $PGHOME/gtm_data
# chown -R postgres.postgres $PGHOME/gtm_data
# su - postgres -c "initgtm -Z gtm -D $PGHOME/gtm_data"

NODE1:

# mkdir -p $PGHOME/data/data_gtm_proxy1
# mkdir -p $PGHOME/data/data_coord1
# mkdir -p $PGHOME/data/data_datanode1
# chown -R postgres.postgres $PGHOME/data/

# su - postgres -c "initdb -D $PGHOME/data/data_coord1/ --nodename coord1"
# su - postgres -c "initdb -D $PGHOME/data/data_datanode1/ --nodename datanode1"
# su - postgres -c "initgtm -D $PGHOME/data/data_gtm_proxy1/ -Z gtm_proxy"

NODE2:

# mkdir -p $PGHOME/data/data_gtm_proxy2
# mkdir -p $PGHOME/data/data_coord2
# mkdir -p $PGHOME/data/data_datanode2
# chown -R postgres.postgres $PGHOME/data/

# su - postgres -c "initdb -D $PGHOME/data/data_coord2/ --nodename coord2"
# su - postgres -c "initdb -D $PGHOME/data/data_datanode2/ --nodename datanode2"
# su - postgres -c "initgtm -D $PGHOME/data/data_gtm_proxy2/ -Z gtm_proxy"

Далее редактируем файлы конфигурации на узлах кластера.

GTM1:

gtm.conf
# vi $PGHOME/gtm_data/gtm.conf
nodename = 'gtm_master'
listen_addresses = '*'
port = 6666
startup = ACT

log_file = 'gtm.log'
log_min_messages = WARNING

GTM2:

gtm.conf
# vi $PGHOME/gtm_data/gtm.conf

nodename = 'gtm_slave'
listen_addresses = '*'
port = 6666
startup = STANDBY

active_host = 'GTM1'       #здесь можно указать IP основного GTM хоста, в моём случае '192.168.1.100'
active_port = 6666

log_file = 'gtm.log'
log_min_messages = WARNING

NODE1:

GTM_PROXY:
gtm_proxy.conf
# vi $PGHOME/data/data_gtm_proxy1/gtm_proxy.conf

nodename = 'gtm_proxy1'
listen_addresses = '*'
port = 6666

gtm_host = 'GTM1'
gtm_port = 6666

log_file = 'gtm_proxy1.log'
log_min_messages = WARNING



COORDINATOR1
postgresql.conf
# vi $PGHOME/data/data_coord1/postgresql.conf

listen_addresses = '*'
port = 5432
pooler_port = 6667

gtm_host = 'localhost'               # здесь должен быть адрес/имя хоста gtm_proxy, в моём случае - это localhost
gtm_port = 6666
pgxc_node_name = 'coord1'


pg_hba.conf
# vi $PGHOME/data/data_coord1/pg_hba.conf

host	all		all		192.168.1.0/24		trust


DATANODE1
postgresql.conf
# vi $PGHOME/data/data_datanode1/postgresql.conf

listen_addresses = '*'
port = 15432
pooler_port = 6668

gtm_host = 'localhost'
gtm_port = 6666
pgxc_node_name = 'datanode1'



pg_hba.conf
# vi $PGHOME/data/data_datanode1/pg_hba.conf

host	all		all		192.168.1.0/24		trust

NODE2:

GTM_PROXY:
gtm_proxy.conf
# vi $PGHOME/data/data_gtm_proxy2/gtm_proxy.conf

nodename = 'gtm_proxy2'
listen_addresses = '*'
port = 6666

gtm_host = 'GTM1'
gtm_port = 6666

log_file = 'gtm_proxy2.log'
log_min_messages = WARNING

COORDINATOR2
postgresql.conf
# vi $PGHOME/data/data_coord2/postgresql.conf

listen_addresses = '*'
port = 5432
pooler_port = 6667

gtm_host = 'localhost'
gtm_port = 6666
pgxc_node_name = 'coord2'

pg_hba.conf
# vi $PGHOME/data/data_coord2/pg_hba.conf

host	all		all		192.168.1.0/24		trust


DATANODE2
postgresql.conf
# vi $PGHOME/data/data_datanode2/postgresql.conf

listen_addresses = '*'
port = 15432
pooler_port = 6668

gtm_host = 'localhost'
gtm_port = 6666
pgxc_node_name = 'datanode2'



pg_hba.conf
# vi $PGHOME/data/data_datanode2/pg_hba.conf

host	all		all		192.168.1.0/24		trust



На этом работа с конфигами закончена. Следующим шагом добавим исключения в файервол CentOS на всех хостах:

# firewall-cmd --zone=public --add-port=5432/tcp --permanent
# firewall-cmd --zone=public --add-port=15432/tcp --permanent
# firewall-cmd --zone=public --add-port=6666/tcp --permanent
# firewall-cmd --zone=public --add-port=6667/tcp --permanent
# firewall-cmd --zone=public --add-port=6668/tcp --permanent
# firewall-cmd --reload

Впрочем для GTM1/GTM2 машин будет достаточно открыть только 6666 порт.

Часть 5. Запуск узлов кластера


Теперь мы добрались непосредственно до запуска узлов кластера. Чтобы запустить узлы кластера нужно выполнить следующие команды на соответствующих узлах от имени postgres пользователя:

# su - postgres
$ gtm_ctl start -Z gtm -D $PGHOME/{data_dir}
$ gtm_ctl start -Z gtm_proxy -D $PGHOME/{data_dir}

$ pg_ctl start -Z datanode -D $PGHOME/{data_dir}
$ pg_ctl start -Z coordinator -D $PGHOME/{data_dir}

Где '{data_dir}' имя соответствующей папки для GTM это: 'data/gtm_data', для datanode1 это: 'data/data_datanode1/' и т.д.

Но я хочу вам показать другой, более удобный способ управления запуском/остановкой/автозапуском.
В папке с исходными кодами есть SysV скрипт для «изящного контроля» PostgreSQL. Наша задача адаптировать его под каждую роль узлов в кластере. Давайте посмотрим что из себя представляет сам скрипт:

src/postgres-xl/contrib/start-scripts/linux
# cat /usr/local/src/postgres-xl/contrib/start-scripts/linux

#! /bin/sh

# chkconfig: 2345 98 02
# description: PostgreSQL RDBMS

# This is an example of a start/stop script for SysV-style init, such
# as is used on Linux systems.  You should edit some of the variables
# and maybe the 'echo' commands.
#
# Place this file at /etc/init.d/postgresql (or
# /etc/rc.d/init.d/postgresql) and make symlinks to
#   /etc/rc.d/rc0.d/K02postgresql
#   /etc/rc.d/rc1.d/K02postgresql
#   /etc/rc.d/rc2.d/K02postgresql
#   /etc/rc.d/rc3.d/S98postgresql
#   /etc/rc.d/rc4.d/S98postgresql
#   /etc/rc.d/rc5.d/S98postgresql
# Or, if you have chkconfig, simply:
# chkconfig --add postgresql
#
# Proper init scripts on Linux systems normally require setting lock
# and pid files under /var/run as well as reacting to network
# settings, so you should treat this with care.

# Original author:  Ryan Kirkpatrick <pgsql@rkirkpat.net>

# contrib/start-scripts/linux

## EDIT FROM HERE

# Installation prefix
prefix=/usr/local/pgsql

# Data directory
PGDATA="/usr/local/pgsql/data"

# Who to run the postmaster as, usually "postgres".  (NOT "root")
PGUSER=postgres

# Where to keep a log file
PGLOG="$PGDATA/serverlog"

# It's often a good idea to protect the postmaster from being killed by the
# OOM killer (which will tend to preferentially kill the postmaster because
# of the way it accounts for shared memory).  Setting the OOM_SCORE_ADJ value
# to -1000 will disable OOM kill altogether.  If you enable this, you probably
# want to compile PostgreSQL with "-DLINUX_OOM_SCORE_ADJ=0", so that
# individual backends can still be killed by the OOM killer.
#OOM_SCORE_ADJ=-1000
# Older Linux kernels may not have /proc/self/oom_score_adj, but instead
# /proc/self/oom_adj, which works similarly except the disable value is -17.
# For such a system, enable this and compile with "-DLINUX_OOM_ADJ=0".
#OOM_ADJ=-17

## STOP EDITING HERE

# The path that is to be used for the script
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin

# What to use to start up the postmaster.  (If you want the script to wait
# until the server has started, you could use "pg_ctl start -w" here.
# But without -w, pg_ctl adds no value.)
DAEMON="$prefix/bin/postmaster"

# What to use to shut down the postmaster
PGCTL="$prefix/bin/pg_ctl"

set -e

# Only start if we can find the postmaster.
test -x $DAEMON ||
{
	echo "$DAEMON not found"
	if [ "$1" = "stop" ]
	then exit 0
	else exit 5
	fi
}


# Parse command line parameters.
case $1 in
  start)
	echo -n "Starting PostgreSQL: "
	test x"$OOM_SCORE_ADJ" != x && echo "$OOM_SCORE_ADJ" > /proc/self/oom_score_adj
	test x"$OOM_ADJ" != x && echo "$OOM_ADJ" > /proc/self/oom_adj
	su - $PGUSER -c "$DAEMON -D '$PGDATA' &" >>$PGLOG 2>&1
	echo "ok"
	;;
  stop)
	echo -n "Stopping PostgreSQL: "
	su - $PGUSER -c "$PGCTL stop -D '$PGDATA' -s -m fast"
	echo "ok"
	;;
  restart)
	echo -n "Restarting PostgreSQL: "
	su - $PGUSER -c "$PGCTL stop -D '$PGDATA' -s -m fast -w"
	test x"$OOM_SCORE_ADJ" != x && echo "$OOM_SCORE_ADJ" > /proc/self/oom_score_adj
	test x"$OOM_ADJ" != x && echo "$OOM_ADJ" > /proc/self/oom_adj
	su - $PGUSER -c "$DAEMON -D '$PGDATA' &" >>$PGLOG 2>&1
	echo "ok"
	;;
  reload)
        echo -n "Reload PostgreSQL: "
        su - $PGUSER -c "$PGCTL reload -D '$PGDATA' -s"
        echo "ok"
        ;;
  status)
	su - $PGUSER -c "$PGCTL status -D '$PGDATA'"
	;;
  *)
	# Print help
	echo "Usage: $0 {start|stop|restart|reload|status}" 1>&2
	exit 1
	;;
esac

exit 0

Для всех ролей копируем этот скрипт в директорию '/etc/rc.d/init.d/' с каким нибудь внятным именем.
У меня вышло примерно так:

# cp /usr/local/src/postgres-xl/contrib/start-scripts/linux /etc/rc.d/init.d/pgxl_gtm
# cp /usr/local/src/postgres-xl/contrib/start-scripts/linux /etc/rc.d/init.d/pgxl_gtm_prx
# cp /usr/local/src/postgres-xl/contrib/start-scripts/linux /etc/rc.d/init.d/pgxl_dn
# cp /usr/local/src/postgres-xl/contrib/start-scripts/linux /etc/rc.d/init.d/pgxl_crd

Далее начинаем адаптировать скрипты под каждый конкретный инстанс на каждом узле. После некоторых небольших модификаций, скрипт для GTM стал выглядеть следующим образом (для удобства я убрал комментарии и незначимые области):

pgxl_gtm
# vi /etc/rc.d/init.d/pgxl_gtm
#! /bin/sh

# chkconfig: 2345 98 02
# description: PostgreSQL RDBMS

# Installation prefix
prefix=/usr/local/pgsql

# Data directory
PGDATA="$prefix/gtm_data"

# Who to run the postmaster as, usually "postgres".  (NOT "root")
PGUSER=postgres

# Where to keep a log file
PGLOG="$PGDATA/serverlog"

# The path that is to be used for the script
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin:$prefix/bin

# What to use to shut down the postmaster
PGCTL="$prefix/bin/gtm_ctl"

# Which cluster role
PGROLE="gtm"

set -e

# Only start if we can find the postmaster.
test -x $PGCTL ||
{
	echo "$PGCTL not found"
	if [ "$1" = "stop" ]
	then exit 0
	else exit 5
	fi
}


# Parse command line parameters.
case $1 in
  start)
	echo -n "Starting PostgreSQL: "
	test x"$OOM_SCORE_ADJ" != x && echo "$OOM_SCORE_ADJ" > /proc/self/oom_score_adj
	test x"$OOM_ADJ" != x && echo "$OOM_ADJ" > /proc/self/oom_adj
	su - $PGUSER -c "$PGCTL start -Z $PGROLE -D '$PGDATA' &" >>$PGLOG 2>&1
	echo "ok"
	;;
  stop)
	echo -n "Stopping PostgreSQL: "
	su - $PGUSER -c "$PGCTL stop -Z $PGROLE -D '$PGDATA' -m fast"
	echo "ok"
	;;
  restart)
	echo -n "Restarting PostgreSQL: "
	su - $PGUSER -c "$PGCTL stop -Z $PGROLE -D '$PGDATA' -m fast -w"
	test x"$OOM_SCORE_ADJ" != x && echo "$OOM_SCORE_ADJ" > /proc/self/oom_score_adj
	test x"$OOM_ADJ" != x && echo "$OOM_ADJ" > /proc/self/oom_adj
	su - $PGUSER -c "$PGCTL start -Z $PGROLE -D '$PGDATA' &" >>$PGLOG 2>&1
	echo "ok"
	;;
  reload)
        echo -n "Reload PostgreSQL: "
        su - $PGUSER -c "$PGCTL restart -Z $PGROLE -D '$PGDATA'"
        echo "ok"
        ;;
  status)
	su - $PGUSER -c "$PGCTL status -Z $PGROLE -D '$PGDATA'"
	;;
  *)
	# Print help
	echo "Usage: $0 {start|stop|restart|reload|status}" 1>&2
	exit 1
	;;
esac

exit 0

Как вы можете видеть я добавил '$PGHOME/bin' в переменную PATH, убрал DAEMON, в PGCTL прописал путь к утилите gtm_ctl в директории '$PGHOME/bin' для управления ролями GTM и GTM_PROXY, так же добавил переменную PGROLE необходимую для запуска узлов кластера.

Для того чтобы использовать такой скрипт для остальных ролей в кластере нужно отредактировать всего лишь 3 переменные: PGDATA, PGROLE, PGCTL.

PGDATA — это путь к директории с данными для данной роли узла.
PGROLE — роль данного инстанса в кластере. Бывает gtm, gtm_proxy, coordinator, datanode.
PGCTL — утилита запуска сервера, для gtm и gtm_proxy это 'gtm_ctl', а для coordinator и datanode это 'pg_ctl'

Приведу полные изменения для остальных узлов в нашем тестовом кластере:

GTM_PROXY1:
pgxl_gtm_prx
# vi /etc/rc.d/init.d/pgxl_gtm_prx

PGDATA="$prefix/data/data_gtm_proxy1"
PGCTL="$prefix/bin/gtm_ctl"
PGROLE="gtm_proxy"


GTM_PROXY2:
pgxl_gtm_prx
# vi /etc/rc.d/init.d/pgxl_gtm_prx

PGDATA="$prefix/data/data_gtm_proxy2"
PGCTL="$prefix/bin/gtm_ctl"
PGROLE="gtm_proxy"


COORDINATOR1:
pgxl_crd
# vi /etc/rc.d/init.d/pgxl_crd

PGDATA="$prefix/data/data_coord1"
PGCTL="$prefix/bin/pg_ctl"
PGROLE="coordinator"


COORDINATOR2:
pgxl_crd
# vi /etc/rc.d/init.d/pgxl_crd

PGDATA="$prefix/data/data_coord2"
PGCTL="$prefix/bin/pg_ctl"
PGROLE="coordinator"


DATANODE1:
pgxl_dn
# vi /etc/rc.d/init.d/pgxl_dn

PGDATA="$prefix/data/data_datanode1"
PGCTL="$prefix/bin/pg_ctl"
PGROLE="datanode"


DATANODE2:
pgxl_dn
# vi /etc/rc.d/init.d/pgxl_dn

PGDATA="$prefix/data/data_datanode2"
PGCTL="$prefix/bin/pg_ctl"
PGROLE="datanode"


Почти готово! Теперь надо сделать эти скрипты исполняемыми, выполнив на каждом узле соответствующую команду:

# chmod a+x /etc/rc.d/init.d/pgxl_gtm
# chmod a+x /etc/rc.d/init.d/pgxl_gtm_prx
# chmod a+x /etc/rc.d/init.d/pgxl_crd
# chmod a+x /etc/rc.d/init.d/pgxl_dn

Теперь добавляем скрипты в атозагрузку:

# chkconfig --add pgxl_gtm
# chkconfig --add pgxl_gtm_prx
# chkconfig --add pgxl_crd
# chkconfig --add pgxl_dn

И запускаем:

# service pgxl_gtm start
# service pgxl_gtm_prx start
# service pgxl_crd start
# service pgxl_dn start

Как прошел запуск можно посмотреть в файле лога в директории данных, а можно выполнить команду:

# service pgxl_gtm status
# service pgxl_gtm_prx status
# service pgxl_crd status
# service pgxl_dn status

Если всё прошло успешно приступаем к настройке узлов.

Часть 6. Настройка узлов кластера


Произведем настройку узлов кластера в соответствии с мануалом:

NODE1
# su - postgres
$ psql -p 5432 -c "DELETE FROM pgxc_node"
$ psql -p 5432 -c "CREATE NODE coord1 WITH (TYPE='coordinator',HOST='192.168.1.102',PORT=5432)"
$ psql -p 5432 -c "CREATE NODE coord2 WITH (TYPE='coordinator',HOST='192.168.1.103',PORT=5432)"
$ psql -p 5432 -c "CREATE NODE datanode1 WITH (TYPE='datanode',HOST='192.168.1.102',PORT=15432)"
$ psql -p 5432 -c "CREATE NODE datanode2 WITH (TYPE='datanode',HOST='192.168.1.103',PORT=15432)"

Проверить что получилось можно с помощью команды:

$ psql -p 5432 -c "select * from pgxc_node"

Если всё в порядке, рестартуем пул:

$ psql -p 5432 -c "select pgxc_pool_reload()"

При успешной конфигурации команда вернет 't', то есть true.

В большинстве мануалов после этого шага приступают создавать тестовые таблицы и выполнять тестовые запросы, но с гарантией в 99,9% я вам скажу — при попытке выполнить INSERT вы получите в логах вот такие записи:
STATEMENT: insert into test select 112233445566, 0123456789;
ERROR: Invalid Datanode number

или вот
STATEMENT: SET global_session TO coord2_21495;SET datestyle TO iso;SET client_min_messages TO notice;SET client_encoding TO UNICODE;SET bytea_output TO escape;
ERROR: Invalid Datanode number
STATEMENT: Remote Subplan
ERROR: node "coord2_21580" does not exist
STATEMENT: SET global_session TO coord2_21580;SET datestyle TO iso;SET client_min_messages TO notice;SET client_encoding TO UNICODE;SET bytea_output TO escape;
ERROR: Invalid Datanode number
STATEMENT: Remote Subplan
ERROR: Invalid Datanode number
STATEMENT: Remote Subplan
ERROR: Invalid Datanode number
STATEMENT: Remote Subplan
LOG: Will fall back to local snapshot for XID = 96184, source = 0, gxmin = 0, autovac launch = 0, autovac = 0, normProcMode = 0, postEnv = 1
ERROR: node "coord2_22428" does not exist
STATEMENT: SET global_session TO coord2_22428;
ERROR: Invalid Datanode number

А всё потому, что в заумных мануалах «для опытных», где всё просто как два пальца об асфальт пропущен важный шаг — заполнение других узлов в самих DATANODE'ах. А делается это довольно просто, на обоих узлах данных в нашей конфигурации выполняем следующее:

$ psql -p 5432 -c "EXECUTE DIRECT ON (datanode1) 'DELETE FROM pgxc_node'"

$ psql -p 5432 -c "EXECUTE DIRECT ON (datanode1) 'create NODE coord1 WITH (TYPE=''coordinator'',HOST=''192.168.1.102'',PORT=5432)'"
$ psql -p 5432 -c "EXECUTE DIRECT ON (datanode1) 'create NODE coord2 WITH (TYPE=''coordinator'',HOST=''192.168.1.103'',PORT=5432)'"
$ psql -p 5432 -c "EXECUTE DIRECT ON (datanode1) 'create NODE datanode1 WITH (TYPE=''datanode'',HOST=''192.168.1.102'',PORT=15432)'"
$ psql -p 5432 -c "EXECUTE DIRECT ON (datanode1) 'create NODE datanode2 WITH (TYPE=''datanode'',HOST=''192.168.1.103'',PORT=15432)'"

$ psql -p 5432 -c "EXECUTE DIRECT ON (datanode1) 'SELECT pgxc_pool_reload()'"

Соответственно строку
EXECUTE DIRECT ON (datanode1)

меняем на
EXECUTE DIRECT ON (datanode2)

для нода номер 2.

И вуаля! Теперь можно смело создавать таблицы и тестировать наш кластер. Но это уже совсем другая история…

Заключение


Вот и всё, всё настроено и всё работает, казалось бы — ничего сложного нет, на за этой статьёй скрывается целая неделя поиска и курения мануалов. Самым безобидным сейчас кажется этап скачки/компиляции и установки исходников, но на самом деле там тоже хватало проблем (конечно же дело в моей неопытности в работе на таком окружении), например код упорно не хотел компилироваться и кидал вот такую ошибку:

'/usr/bin/perl' /bin/collateindex.pl -f -g -i 'bookindex' -o bookindex.sgml HTML.index
Can't open perl script "/bin/collateindex.pl": No such file or directory
make[4]: *** [bookindex.sgml] Error 2
make[4]: Leaving directory `/usr/local/src/postgres-xl/doc-xc/src/sgml'
make[3]: *** [sql_help.h] Error 2
make[3]: Leaving directory `/usr/local/src/postgres-xl/src/bin/psql'
make[2]: *** [all-psql-recurse] Error 2
make[2]: Leaving directory `/usr/local/src/postgres-xl/src/bin'
make[1]: *** [all-bin-recurse] Error 2
make[1]: Leaving directory `/usr/local/src/postgres-xl/src'
make: *** [all-src-recurse] Error 2

Позже на каком-то китайском форуме нашёл ответ, что нужно установить библиотеку docbook-style-dsssl и так далее, каждый новый сюрприз заводил меня в тупик из-за отсутствия опыта и полных мануалов (для чайников, таких как я) как таковых.

Но всё же после недели поиска информации, сотен проб и ошибок всё получилось и кластер завелся.
Надеюсь кому-то эта публикация хоть сколечко облегчит жизнь или будет полезна.

Дальше я планирую заняться настройкой Load-Balance, мигрировать базу из обычного PostgreSQL 9.4 под управлением Windows в собранный кластер postgres-xl 9.2 на CentOS 7.0, как следует протестировать самые тяжелые запросы в нашем проекте уже в кластере, сравнить с результатами Standalone PostgreSQL, заняться тюнингом настроек кластера, поиграться с PostGIS в кластере и т.д. Так что, если хабровчанам будет полезна эта статья или что-либо из того, что я перечислил — с удовольствием поделюсь этим с вами.

Спасибо за внимание.

Similar posts

AdBlock has stolen the banner, but banners are not teeth — they will be back

More
Ads

Comments 20

    +1
    интересно, пишите еще! Очень интересен опыт использования кластера — насколько стабилен, какие проблемы всплывают и когда. ну и все такое.
      +1
      Спасибо за оценку, если всё пойдёт гладко, то подобный кластер будет использоваться в продакшене, поэтому материалов для будущих статей будет достаточно.
        0
        я смотрю, что всё пошло не гладко?
          0
          Увы, сменил место работы, в новом проекте не используется ни PosgreSQL, ни кластеризация. А времени позаниматься экспериментами на досуге уже не хватает.

          PS: По итогу мои занятия кластером так и остались факультативными, проект был зарелижен с 1 инстансом Postgres.
      –3
      «который никогда прежде не занимался кластеризацией и тем более никогда прежде не работал в линукс-подобных осях»
      «подобный кластер будет использоваться в продакшене»
        +3
        Вы предлагаете ему ничего не делать?
          –5
          Кому? Кластеру?

          Я к тому, что мы идём по какому то неверному пути, раз у нас кластеры для продакшена стали разворачивать люди, которые с линуксом даже никогда не работали. Вроде не вижу на рынке недостаток в специалистах с опытом и знаниями.
          0
          Как я понял вы сразу родились со скиллом 80lvl?
            0
            Нет, вы неверно поняли, я для этого долго учился, прежде чем стал работать с чем то большим и серьёзным.
              +2
              Топикстартер тоже учится. Пусть он десять раз наступит на грабли, но зато получит опыт. Можно долго учится, но при этом на практике показать нулевой результат.
                0
                Вы видимо вообще не верно трактуете мой каммент. Лично к ТС у меня вообще никаких претензий нет, он за пару вечеров и без знания новой для него системы собрал кластер и он работает — отлично. Я сам такими вещами занимаюсь постоянно. Я говорю о ситуации в целом. Представим что у ТС этот кластер обслуживает базу какого-нить медицинского учреждения (ну понятно что не государственного :) но и явно не два бухгалтера продуктового магазина на нём работают), завтра он вводит этот кластер в продашен, после завтра этот кластер по любой из миллиона причин — падает. Я более чем уверен что ТС его даже поднимет, разберётся в логах и тд, вопрос только в том, что у него на этой уйдёт в Х раз больше времени чем и опытного специалиста, а просто ведёт за собой неработоспособность организации, а я напомню что в примере у нас мед.учреждение. Соответственно придёте вы такой после завтра с переломом ноги, а вам скажут «а мы не можем вашу карточку у нас найти, мы не знаем что вы заплатили стопицот миллионов и являетесь нашим клиентом», а у вас сложный перелом ноги в 10 местах, открытый… НУ это я просто к примеру, против лично вас я то же ничего не имею и ттт, что б с вами всё было хорошо.
                А при этом откройте любой сайт с вакансиями — специалистов с опытом — огромное количество! Да, я понимаю что кризис, но когда уже перестанут экономить на специалистах в области IT? Ведь это ведёт к прямым и зачастую очень высоким убыткам для самой компании. Я вот об этом говорю.
                  0
                  У нас менталитет такой.
                  Купить за 100к MacBookPro и зажать пару баксов в месяц на VPN что бы послушать музыку на spotify(Реальный пример из жизни)

                  Скажу так. В небольших компаниях достаточно часто вижу практику спонтанных решений. Есть специалист в компании, который поддерживает сервачек на которой крутится 1 БД, а тут бац и срочно, вот прям вчера нужно распределить нагрузку из-за того, что на 20 человек больше прибежало на сайт(образно).

                  В любом случае, автор молодец, что не побоялся заглянуть «под капот».
                    –1
                    Знаете, в небольших компаниях я то же поработал, и мне кажется одним из скиллов хорошего специалиста должно быть как раз умение объяснить начальнику чем чревато такое решение
                      +1
                      Начальники и ситуации разные бывают.
                    0
                    >Представим что у ТС этот кластер обслуживает базу какого-нить медицинского учреждения
                    представили. а теперь давайте попытаемся понять, что приведенный Вами пример — это вопрос ответственности закупщика услуг и, немного, *этики* исполнителя(в Вашем примере — топикстартер). Но никак не вопрос *компетентности* ТС, так как закупы уже решили — его компетенций достаточно и готовы платить за это денег.
                    Как то так.
                      0
                      Ну начнём с того, что закупщик услуг может вообще не знать кто именно обслуживает данную систему и о его компетенциях, это знает лишь исполнитель и его руководитель. И дело не в «этике», а в ОТВЕТСТВЕННОСТИ! Не нужно путать эти понятия. Лично мне и в голову не придётся взяться обслуживать в продакшене систему, с которой я знаком 5 минут, даже учитывая свой немалый опыт и если даже допустить что я буду работать у такого дебила-руководителя (хотя скорее всего это будет для меня поводом к увольнению, тк ничего хорошего от такого руководства ждать не стоит), который мне это предложит. Но почему то многие начинающие специалисты не в состоянии верно оценить свою ответственность перед работодателем и пользователями и берутся за реализацию того, что они просто не в состоянии потянуть в силу отсутствия квалификации. У меня уже есть опыт разгребания мега-крутых в плане оборудования и технологий систем после таких специалистов, которые просто учились на этом, и как вы можете прекрасно догадаться — работало оно соответствующим образом.
            +4
            Здравствуйте, спасибо всем за ваши комментарии. Отвечу сразу на возникшие мнения. Да действительно всю свою карьеру, на всех проектах в которых я участвовал использовали standalone MS SQL сервера бд, да у меня не было опыта работы с линуксом и по кластеризации были лишь теоретические знания. Не буду описывать как мы пришли к решению использовать на этом проекте PostgreSQL, а в последующем использовать кластеризацию для распределения нагрузок и как я пришёл к Postgres-xl. На данном этапе есть необходимость развернуть кластер в тестовом режиме и, как я говорил ранее, если всё пойдёт гладко, то есть кластер оправдает наши ожидания и выдержит все тесты, только после этого будет приниматься окончательное решение о его развертывании в продакшене. Само собой я понимаю риски которые описал товарищ KorP, само собой я буду нести полную ответственность за скорость и качество восстановления работоспособности системы перед организацией. Именно поэтому я и хотел поделиться с хабровчанами тем, как я на практике реализовал такую архитектуру в postgres-xl, какие были проблемы и подводные камни, и какие решения я находил. Ну а по поводу осуждений в неопытности и выходе в продакшен — так можно сказать о любом разработчики на любом проекте, который в определённый момент захотел внедрить новую технологию, в которой у него не было опыта работы. Например одну из моих первых команд, разрабатывавших сайт на классическом ASP.Net с таким подходом надо было поувольнять после выхода MVC и набрать уже поднаторевших ребят на этой технологии. Но в итоге попробовали, изучили, освоили и успешно справлялись со своими задачами. Поэтому и в этой ситуации не вижу ничего плохого в том чтобы освоить новую СУБД, новую архитектуру и выйти с ней в продакшен.
              0
              Похоже, что-то случилось с компанией, которая занималась разработкой Postgres-xl
              twitter.com/andy_pavlo/status/616317581297893377
              twitter.com/SQLScottGleason/status/609082014071947265
              0
              Drakula2k спасибо за наводку, нечто такое я подозревал, когда видел что в репозитории postgres-xl действительно всего несколько коммитов в этом году, видимо придётся искать другое решение — PostgreSQL + pgpool-II например.

              Only users with full accounts can post comments. Log in, please.