1# contrib/pglogical/Makefile
2
3MODULE_big = pglogical
4EXTENSION = pglogical
5PGFILEDESC = "pglogical - logical replication"
6
7MODULES = pglogical_output
8
9DATA = pglogical--1.0.0.sql pglogical--1.0.0--1.0.1.sql \
10	   pglogical--1.0.1--1.1.0.sql \
11	   pglogical--1.1.0--1.1.1.sql pglogical--1.1.1--1.1.2.sql \
12	   pglogical--1.1.2--1.2.0.sql \
13	   pglogical--1.2.0--1.2.1.sql pglogical--1.2.1--1.2.2.sql \
14	   pglogical--1.2.2--2.0.0.sql \
15	   pglogical--2.0.0--2.0.1.sql \
16	   pglogical--2.0.0--2.1.0.sql pglogical--2.0.1--2.1.0.sql \
17	   pglogical--2.1.0--2.1.1.sql pglogical--2.1.1--2.2.0.sql \
18	   pglogical--2.2.0.sql \
19	   pglogical--2.2.0--2.2.1.sql pglogical--2.2.1.sql \
20	   pglogical--2.2.1--2.2.2.sql pglogical--2.2.2.sql \
21	   pglogical--2.2.2--2.3.0.sql \
22	   pglogical--2.2.2--2.3.1.sql \
23	   pglogical--2.3.0.sql \
24	   pglogical--2.3.0--2.3.1.sql \
25	   pglogical--2.3.1.sql \
26	   pglogical--2.3.1--2.3.2.sql \
27	   pglogical--2.3.2.sql \
28	   pglogical--2.3.2--2.3.3.sql \
29	   pglogical--2.3.3.sql \
30	   pglogical--2.3.3--2.3.4.sql \
31	   pglogical--2.3.4.sql \
32	   pglogical--2.3.4--2.4.0.sql \
33	   pglogical--2.4.0.sql
34
35OBJS = pglogical_apply.o pglogical_conflict.o pglogical_manager.o \
36	   pglogical.o pglogical_node.o pglogical_relcache.o \
37	   pglogical_repset.o pglogical_rpc.o pglogical_functions.o \
38	   pglogical_queue.o pglogical_fe.o pglogical_worker.o \
39	   pglogical_sync.o pglogical_sequences.o pglogical_executor.o \
40	   pglogical_dependency.o pglogical_apply_heap.o pglogical_apply_spi.o \
41	   pglogical_output_config.o pglogical_output_plugin.o \
42	   pglogical_output_proto.o pglogical_proto_json.o \
43	   pglogical_proto_native.o pglogical_monitoring.o
44
45SCRIPTS_built = pglogical_create_subscriber
46
47REGRESS = preseed infofuncs init_fail init preseed_check basic extended conflict_secondary_unique \
48		  toasted replication_set add_table matview bidirectional primary_key \
49		  interfaces foreign_key functions copy triggers parallel row_filter \
50		  row_filter_sampling att_list column_filter apply_delay multiple_upstreams \
51		  node_origin_cascade drop
52
53EXTRA_CLEAN += compat94/pglogical_compat.o compat95/pglogical_compat.o \
54			   compat96/pglogical_compat.o compat10/pglogical_compat.o \
55			   compat11/pglogical_compat.o compat11/pglogical_compat.bc \
56			   compat12/pglogical_compat.o compat12/pglogical_compat.bc \
57			   compat13/pglogical_compat.o compat13/pglogical_compat.bc \
58			   pglogical_create_subscriber.o
59
60# The # in #define is taken as a comment, per https://bugs.debian.org/cgi-bin/bugreport.cgi?bug=142043
61# so it must be escaped. The $ placeholders in awk must be doubled too.
62pglogical_version=$(shell awk '/\#define PGLOGICAL_VERSION[ \t]+\".*\"/ { print substr($$3,2,length($$3)-2) }' $(realpath $(srcdir)/pglogical.h) )
63
64# For regression checks
65# http://www.postgresql.org/message-id/CAB7nPqTsR5o3g-fBi6jbsVdhfPiLFWQ_0cGU5=94Rv_8W3qvFA@mail.gmail.com
66# this makes "make check" give a useful error
67abs_top_builddir = .
68NO_TEMP_INSTALL = yes
69
70PG_CONFIG ?= pg_config
71
72PGVER := $(shell $(PG_CONFIG) --version | sed 's/[^0-9]//g' | cut -c 1-2)
73
74PG_CPPFLAGS += -I$(libpq_srcdir) -I$(realpath $(srcdir)/compat$(PGVER)) -Werror=implicit-function-declaration
75SHLIB_LINK += $(libpq) $(filter -lintl, $(LIBS))
76
77OBJS += $(srcdir)/compat$(PGVER)/pglogical_compat.o
78
79ifeq ($(PGVER),94)
80DATA += compat94/pglogical_origin.control compat94/pglogical_origin--1.0.0.sql
81REGRESS = preseed infofuncs init preseed_check basic extended \
82		  toasted replication_set add_table matview primary_key \
83		  interfaces foreign_key functions copy triggers parallel \
84		  att_list column_filter apply_delay multiple_upstreams \
85		  node_origin_cascade drop
86
87REGRESS += --dbname=regression
88SCRIPTS_built += pglogical_dump/pglogical_dump
89SCRIPTS += pglogical_dump/pglogical_dump
90requires = requires=pglogical_origin
91control_path = $(abspath $(abs_top_builddir))/pglogical.control
92else
93DATA += pglogical_origin.control pglogical_origin--1.0.0.sql
94requires =
95control_path = $(abspath $(srcdir))/pglogical.control
96endif
97
98EXTRA_CLEAN += $(control_path)
99
100
101PGXS = $(shell $(PG_CONFIG) --pgxs)
102include $(PGXS)
103
104
105ifeq ($(PGVER),94)
106regresscheck: ;
107check: ;
108
109$(srcdir)/pglogical_dump/pg_dump.c:
110	$(warning pglogical_dump empty, trying to fetch as submodule)
111	git submodule init
112	git submodule update
113
114pglogical_dump/pglogical_dump: pglogical_dump/pg_dump.c
115
116SUBDIRS += pglogical_dump
117
118else
119# We can't do a normal 'make check' because PGXS doesn't support
120# creating a temp install. We don't want to use a normal PGXS
121# 'installcheck' though, because it's a pain to set up a temp install
122# manually, with the config overrides needed.
123#
124# We compromise by using the install we're building against, installing
125# glogical into it, then making a temp instance. This means that 'check'
126# affects the target DB install. Nobody with any sense runs 'make check'
127# under a user with write permissions to their production PostgreSQL
128# install (right?)
129# But this is still not ideal.
130regresscheck:
131	$(MKDIR_P) regression_output
132	$(pg_regress_check) \
133	    --temp-config ./regress-postgresql.conf \
134	    --temp-instance=./tmp_check \
135	    --outputdir=./regression_output \
136	    --create-role=logical \
137	    $(REGRESS)
138
139check: install regresscheck
140
141endif
142
143pglogical_create_subscriber: pglogical_create_subscriber.o pglogical_fe.o
144	$(CC) $(CFLAGS) $^ $(LDFLAGS) $(LDFLAGS_EX) $(libpq_pgport) $(filter-out -lreadline, $(LIBS)) -o $@$(X)
145
146
147pglogical.control: pglogical.control.in pglogical.h
148	sed 's/__PGLOGICAL_VERSION__/$(pglogical_version)/;s/__REQUIRES__/$(requires)/' $(realpath $(srcdir)/pglogical.control.in) > $(control_path)
149
150all: pglogical.control
151
152GITHASH=$(shell if [ -e .distgitrev ]; then cat .distgitrev; else git rev-parse --short HEAD; fi)
153
154dist-common: clean
155	@if test "$(wanttag)" -eq 1 -a "`git name-rev --tags --name-only $(GITHASH)`" = "undefined"; then echo "cannot 'make dist' on untagged tree; tag it or use make git-dist"; exit 1; fi
156	@rm -f .distgitrev .distgittag
157	@if ! git diff-index --quiet HEAD; then echo >&2 "WARNING: git working tree has uncommitted changes to tracked files which were INCLUDED"; fi
158	@if [ -n "`git ls-files --exclude-standard --others`" ]; then echo >&2 "WARNING: git working tree has unstaged files which were IGNORED!"; fi
159	@echo $(GITHASH) > .distgitrev
160	@git name-rev --tags --name-only `cat .distgitrev` > .distgittag
161	@(git ls-tree -r -t --full-tree HEAD --name-only \
162	  && cd pglogical_dump\
163	  && git ls-tree -r -t --full-tree HEAD --name-only | sed 's/^/pglogical_dump\//'\
164	 ) |\
165	  tar cjf "${distdir}.tar.bz2" --transform="s|^|${distdir}/|" --no-recursion \
166	    -T - .distgitrev .distgittag
167	@echo >&2 "Prepared ${distdir}.tar.bz2 for rev=`cat .distgitrev`, tag=`cat .distgittag`"
168	@rm -f .distgitrev .distgittag
169	@md5sum "${distdir}.tar.bz2" > "${distdir}.tar.bz2.md5"
170	@if test -n "$(GPGSIGNKEYS)"; then gpg -q -a -b $(shell for x in $(GPGSIGNKEYS); do echo -u $$x; done) "${distdir}.tar.bz2"; else echo "No GPGSIGNKEYS passed, not signing tarball. Pass space separated keyid list as make var to sign."; fi
171
172dist: distdir=pglogical-$(pglogical_version)
173dist: wanttag=1
174dist: dist-common
175
176git-dist: distdir=pglogical-$(pglogical_version)_git$(GITHASH)
177git-dist: wanttag=0
178git-dist: dist-common
179
180
181# runs TAP tests
182
183# PGXS doesn't support TAP tests yet.
184# Copy perl modules in postgresql_srcdir/src/test/perl
185# to postgresql_installdir/lib/pgxs/src/test/perl
186
187
188define prove_check
189rm -rf $(CURDIR)/tmp_check/log
190cd $(srcdir) && TESTDIR='$(CURDIR)' $(with_temp_install) PGPORT='6$(DEF_PGPORT)' PG_REGRESS='$(top_builddir)/src/test/regress/pg_regress' $(PROVE) --verbose $(PG_PROVE_FLAGS) $(PROVE_FLAGS) $(or $(PROVE_TESTS),t/*.pl)
191endef
192
193check_prove:
194	$(prove_check)
195
196.PHONY: all check regresscheck pglogical.control
197
198define _pgl_create_recursive_target
199.PHONY: $(1)-$(2)-recurse
200$(1): $(1)-$(2)-recurse
201$(1)-$(2)-recurse: $(if $(filter check, $(3)), temp-install)
202	$(MKDIR_P) $(2)
203	$$(MAKE) -C $(2) -f $(abspath $(srcdir))/$(2)/Makefile VPATH=$(abspath $(srcdir))/$(2) $(3)
204endef
205
206$(foreach target,$(if $1,$1,$(standard_targets)),$(foreach subdir,$(if $2,$2,$(SUBDIRS)),$(eval $(call _pgl_create_recursive_target,$(target),$(subdir),$(if $3,$3,$(target))))))
207
208
209#
210# The following hideous hack works around pg_regress's inability to inject
211# prefix commands by using a wrapper 'postgres' that finds the real postgres.
212#
213
214define VALGRIND_WRAPPER
215#!/bin/bash
216
217set -e -u -x
218
219# May also want --expensive-definedness-checks=yes
220#
221# Quicker runs without --track-origins=yes --read-var-info=yes
222#
223# If you don't want leak checking, use --leak-check=no
224#
225# When just doing leak checking and not looking for detailed memory error reports you don't need:
226# 	--track-origins=yes --read-var-info=yes --malloc-fill=8f --free-fill=9f
227#
228SUPP=$(POSTGRES_SRC)/src/tools/valgrind.supp
229
230# Pop top two elements from path; the first is added by pg_regress
231# and the next is us.
232function join_by { local IFS="$$1"; shift; echo "$$*"; }
233IFS=':' read -r -a PATHA <<< "$$PATH"
234export PATH=$$(join_by ":" "$${PATHA[@]:2}")
235
236NEXT_POSTGRES=$$(which postgres)
237if [ "$${NEXT_POSTGRES}" -ef "./valgrind/postgres" ]; then
238    echo "ERROR: attempt to execute self"
239    exit 1
240fi
241
242echo "Running $${NEXT_POSTGRES} under Valgrind"
243
244valgrind --leak-check=full --show-leak-kinds=definite,possible,reachable --gen-suppressions=all \
245	--suppressions="$${SUPP}" --suppressions=`pwd`/pglogical.supp --verbose \
246	--time-stamp=yes  --log-file=valgrind-$$$$-%p.log --trace-children=yes \
247	--track-origins=yes --read-var-info=yes --malloc-fill=8f --free-fill=9f \
248	--num-callers=30 \
249	postgres "$$@"
250
251endef
252
253export VALGRIND_WRAPPER
254
255valgrind-check:
256	$(if $(POSTGRES_SRC),,$(error set Make variable POSTGRES_SRC to postgres source dir to find valgrind.supp))
257	$(if $(wildcard $(POSTGRES_SRC)/src/tools/valgrind.supp),,$(error missing valgrind suppressions at $(POSTGRES_SRC)/src/tools/valgrind.supp))
258	mkdir -p valgrind/
259	echo "$$VALGRIND_WRAPPER" > valgrind/postgres
260	chmod a+x valgrind/postgres
261	PATH=./valgrind/:$(PATH) $(MAKE) check
262	rm valgrind/postgres
263