Skip to content

Commit 500563f

Browse files
committed
Add support for PostgreSQL 10
The extension now works with PostgreSQL 10, while retaining compatibility with version 9.6. PostgreSQL 10 has numerous internal changes to functions and APIs, which necessitates various glue code and compatibility wrappers to seamlessly retain backwards compatiblity with older versions. Test output might also differ between versions. In particular, the psql client generates version-specific output with `\d` and EXPLAINs might differ due to new query optimizations. The test suite has been modified as follows to handle these issues. First, tests now use version-independent functions to query system catalogs instead of using `\d`. Second, changes have been made to the test suite to be able to verify some test outputs against version-dependent reference files.
1 parent bd36e6d commit 500563f

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

76 files changed

+2645
-2993
lines changed

.travis.yml

Lines changed: 17 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -1,24 +1,26 @@
11
sudo: required
2-
32
language: c
4-
os: linux
5-
dist: trusty
6-
3+
os:
4+
- linux
75
services:
86
- docker
7+
env:
8+
- PG_VERSION=9.6.5
9+
- PG_VERSION=10.0
10+
11+
before_install:
12+
- docker run -d --name pgbuild -v ${TRAVIS_BUILD_DIR}:/build postgres:${PG_VERSION}-alpine
13+
install:
14+
- docker exec -it pgbuild /bin/sh -c "apk add --no-cache --virtual .build-deps coreutils dpkg-dev gcc libc-dev make util-linux-dev diffutils cmake && mkdir -p /build/debug && cd /build/debug && cmake .. -DCMAKE_BUILD_TYPE=Debug && make install && chown -R postgres:postgres /build/"
15+
script:
16+
- docker exec -u postgres -it pgbuild /bin/sh -c "make -C /build/debug installcheck PG_REGRESS_OPTS='--temp-instance=/tmp/pgdata'"
17+
after_failure:
18+
- docker exec -it pgbuild cat /build/debug/test/regression.diffs
19+
after_script:
20+
- docker rm -f pgbuild
921

1022
jobs:
1123
include:
1224
- stage: test
13-
before_install:
14-
- docker run -d --name pgbuild -v ${TRAVIS_BUILD_DIR}:/build postgres:9.6.3-alpine
15-
install:
16-
- docker exec -it pgbuild /bin/sh -c "apk add --no-cache --virtual .build-deps coreutils dpkg-dev gcc libc-dev make util-linux-dev diffutils cmake && mkdir -p /build/debug && cd /build/debug && cmake .. -DCMAKE_BUILD_TYPE=Debug && make install && chown -R postgres:postgres /build/"
1725
script:
18-
- docker exec -u postgres -it pgbuild /bin/sh -c "make -C /build/debug installcheck PG_REGRESS_OPTS='--temp-instance=/tmp/pgdata'"
19-
after_failure:
20-
- docker exec -it pgbuild cat /build/debug/test/regression.diffs
21-
after_script:
22-
- docker rm -f pgbuild
23-
- stage: test
24-
script: PGTEST_TMPDIR=$TRAVIS_BUILD_DIR bash -x ./scripts/test_updates.sh
26+
- PGTEST_TMPDIR=/tmp/ bash -x ./scripts/test_updates.sh

CMakeLists.txt

Lines changed: 11 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -58,21 +58,26 @@ execute_process(
5858
OUTPUT_VARIABLE PG_VERSION_STRING
5959
OUTPUT_STRIP_TRAILING_WHITESPACE)
6060

61-
if (NOT ${PG_VERSION_STRING} MATCHES "^PostgreSQL[ ]+([0-9]+)\\.([0-9]+)\\.([0-9]+)$")
61+
if (NOT ${PG_VERSION_STRING} MATCHES "^PostgreSQL[ ]+([0-9]+)\\.([0-9]+)(\\.([0-9]+))*$")
6262
message(FATAL_ERROR "Could not parse PostgreSQL version ${PG_VERSION}")
6363
endif ()
6464

6565
set(PG_VERSION_MAJOR ${CMAKE_MATCH_1})
6666
set(PG_VERSION_MINOR ${CMAKE_MATCH_2})
67-
set(PG_VERSION_PATCH ${CMAKE_MATCH_3})
68-
set(PG_VERSION "${PG_VERSION_MAJOR}.${PG_VERSION_MINOR}.${PG_VERSION_PATCH}")
67+
set(PG_VERSION_PATCH ${CMAKE_MATCH_4})
68+
69+
if (NOT ${PG_VERSION_PATCH} OR ${PG_VERSION_PATCH} EQUAL "")
70+
set(PG_VERSION "${PG_VERSION_MAJOR}.${PG_VERSION_MINOR}")
71+
else ()
72+
set(PG_VERSION "${PG_VERSION_MAJOR}.${PG_VERSION_MINOR}.${PG_VERSION_PATCH}")
73+
endif ()
6974

7075
message(STATUS "Compiling against PostgreSQL version ${PG_VERSION}")
7176

7277
if ((${PG_VERSION} VERSION_LESS "9.6")
73-
OR (${PG_VERSION} VERSION_EQUAL "10")
74-
OR (${PG_VERSION} VERSION_GREATER "10"))
75-
message(FATAL_ERROR "TimescaleDB only supports PostgreSQL 9.6")
78+
OR (${PG_VERSION} VERSION_EQUAL "11")
79+
OR (${PG_VERSION} VERSION_GREATER "11"))
80+
message(FATAL_ERROR "TimescaleDB only supports PostgreSQL 9.6 or 10")
7681
endif ()
7782

7883
# Get PostgreSQL configuration from pg_config

scripts/docker-build.sh

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5,7 +5,8 @@
55
#
66
SCRIPT_DIR=$(dirname $0)
77
BASE_DIR=${PWD}/${SCRIPT_DIR}/..
8-
PG_IMAGE_TAG=${PG_IMAGE_TAG:-9.6.3-alpine}
8+
PG_VERSION=${PG_VERSION:-10.0}
9+
PG_IMAGE_TAG=${PG_IMAGE_TAG:-${PG_VERSION}-alpine}
910
BUILD_CONTAINER_NAME=${BUILD_CONTAINER_NAME:-pgbuild}
1011
BUILD_IMAGE_NAME=${BUILD_IMAGE_NAME:-$USER/pgbuild}
1112
IMAGE_NAME=${IMAGE_NAME:-$USER/timescaledb}

scripts/test_updates.sh

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -8,13 +8,17 @@ BASE_DIR=${PWD}/${SCRIPT_DIR}/..
88
PGTEST_TMPDIR=${PGTEST_TMPDIR:-$(mktemp -d 2>/dev/null || mktemp -d -t 'timescaledb_update_test')}
99
UPDATE_PG_PORT=${UPDATE_PG_PORT:-6432}
1010
CLEAN_PG_PORT=${CLEAN_PG_PORT:-6433}
11-
11+
PG_VERSION=${PG_VERSION:-9.6.5} # Need 9.6.x version since we are
12+
# upgrading the extension from
13+
# versions that didn't support PG10.
1214
UPDATE_FROM_IMAGE=${UPDATE_FROM_IMAGE:-timescale/timescaledb}
1315
UPDATE_FROM_TAG=${UPDATE_FROM_TAG:-0.1.0}
1416
UPDATE_TO_IMAGE=${UPDATE_TO_IMAGE:-update_test}
1517
UPDATE_TO_TAG=${UPDATE_TO_TAG:-latest}
1618
DO_CLEANUP=true
1719

20+
export PG_VERSION
21+
1822
while getopts "d" opt;
1923
do
2024
case $opt in
@@ -142,4 +146,3 @@ docker_pgcmd timescaledb-clean-restore "ALTER DATABASE single SET timescaledb.re
142146

143147
echo "Testing restored"
144148
docker_pgdiff timescaledb-updated timescaledb-clean-restore /src/test/sql/updates/test-0.1.1.sql
145-

sql/ddl_api.sql

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -89,6 +89,9 @@ BEGIN
8989
USING ERRCODE = 'IO102';
9090
END IF;
9191

92+
-- Validate that the hypertable supports the triggers in the main table
93+
PERFORM _timescaledb_internal.validate_triggers(main_table);
94+
9295
time_type := _timescaledb_internal.dimension_type(main_table, time_column_name, true);
9396

9497
chunk_time_interval_actual := _timescaledb_internal.time_interval_specification_to_internal(

sql/util_internal_table_ddl.sql

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -221,3 +221,6 @@ BEGIN
221221
END LOOP;
222222
END
223223
$BODY$;
224+
225+
CREATE OR REPLACE FUNCTION _timescaledb_internal.validate_triggers(main_table REGCLASS) RETURNS VOID
226+
AS '$libdir/timescaledb', 'hypertable_validate_triggers' LANGUAGE C IMMUTABLE STRICT;

src/CMakeLists.txt

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,6 +51,7 @@ set(HEADERS
5151
hypertable.h
5252
hypertable_insert.h
5353
indexing.h
54+
parse_rewrite.h
5455
partitioning.h
5556
planner_utils.h
5657
process_utility.h
@@ -89,6 +90,8 @@ set(SOURCES
8990
hypertable_insert.c
9091
indexing.c
9192
init.c
93+
parse_analyze.c
94+
parse_rewrite.c
9295
partitioning.c
9396
planner.c
9497
planner_utils.c

src/catalog.c

Lines changed: 27 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,14 @@
1212
#include <commands/sequence.h>
1313
#include <access/xact.h>
1414

15+
#include "compat.h"
1516
#include "catalog.h"
1617
#include "extension.h"
1718

19+
#if PG10
20+
#include <utils/regproc.h>
21+
#endif
22+
1823
static const char *catalog_table_names[_MAX_CATALOG_TABLES] = {
1924
[HYPERTABLE] = HYPERTABLE_TABLE_NAME,
2025
[DIMENSION] = DIMENSION_TABLE_NAME,
@@ -360,14 +365,32 @@ catalog_table_next_seq_id(Catalog *catalog, enum CatalogTable table)
360365
return DatumGetInt64(DirectFunctionCall1(nextval_oid, ObjectIdGetDatum(relid)));
361366
}
362367

368+
#if PG96
369+
#define CatalogTupleInsert(relation, tuple) \
370+
do { \
371+
simple_heap_insert(relation, tuple); \
372+
CatalogUpdateIndexes(relation, tuple); \
373+
} while (0);
374+
375+
#define CatalogTupleUpdate(relation, tid, tuple) \
376+
do { \
377+
simple_heap_update(relation, tid, tuple); \
378+
CatalogUpdateIndexes(relation, tuple); \
379+
} while (0);
380+
381+
#define CatalogTupleDelete(relation, tid) \
382+
simple_heap_delete(relation, tid);
383+
384+
#endif /* PG96 */
385+
363386
/*
364387
* Insert a new row into a catalog table.
365388
*/
366389
void
367390
catalog_insert(Relation rel, HeapTuple tuple)
368391
{
369-
simple_heap_insert(rel, tuple);
370-
CatalogUpdateIndexes(rel, tuple);
392+
CatalogTupleInsert(rel, tuple);
393+
371394
/* Make changes visible */
372395
CommandCounterIncrement();
373396
}
@@ -387,16 +410,15 @@ catalog_insert_values(Relation rel, TupleDesc tupdesc, Datum *values, bool *null
387410
void
388411
catalog_update(Relation rel, HeapTuple tuple)
389412
{
390-
simple_heap_update(rel, &tuple->t_self, tuple);
391-
CatalogUpdateIndexes(rel, tuple);
413+
CatalogTupleUpdate(rel, &tuple->t_self, tuple);
392414
/* Make changes visible */
393415
CommandCounterIncrement();
394416
}
395417

396418
void
397419
catalog_delete_tid(Relation rel, ItemPointer tid)
398420
{
399-
simple_heap_delete(rel, tid);
421+
CatalogTupleDelete(rel, tid);
400422
CommandCounterIncrement();
401423
}
402424

src/chunk.c

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -315,7 +315,7 @@ chunk_create_after_lock(Hypertable *ht, Point *p, const char *schema, const char
315315

316316
chunk->table_id = get_relname_relid(NameStr(chunk->fd.table_name), schema_oid);
317317

318-
trigger_create_on_all_chunks(ht, chunk);
318+
trigger_create_all_on_chunk(ht, chunk);
319319

320320
/* Create all indexes on the chunk */
321321
chunk_index_create_all(ht->fd.id, ht->main_table_relid, chunk->fd.id, chunk->table_id);

src/chunk_dispatch.c

Lines changed: 12 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -13,20 +13,21 @@
1313
ChunkDispatch *
1414
chunk_dispatch_create(Hypertable *ht, EState *estate, Query *parse)
1515
{
16-
ChunkDispatch *cp = palloc(sizeof(ChunkDispatch));
16+
ChunkDispatch *cd = palloc0(sizeof(ChunkDispatch));
1717

18-
cp->hypertable = ht;
19-
cp->estate = estate;
20-
cp->hypertable_result_rel_info = NULL;
21-
cp->parse = parse;
22-
cp->cache = subspace_store_init(ht->space->num_dimensions, estate->es_query_cxt);
23-
return cp;
18+
cd->hypertable = ht;
19+
cd->estate = estate;
20+
cd->hypertable_result_rel_info = NULL;
21+
cd->parse = parse;
22+
cd->cache = subspace_store_init(ht->space->num_dimensions, estate->es_query_cxt);
23+
24+
return cd;
2425
}
2526

2627
void
27-
chunk_dispatch_destroy(ChunkDispatch *cp)
28+
chunk_dispatch_destroy(ChunkDispatch *cd)
2829
{
29-
subspace_store_free(cp->cache);
30+
subspace_store_free(cd->cache);
3031
}
3132

3233
static void
@@ -40,7 +41,7 @@ destroy_chunk_insert_state(void *cis)
4041
* partitioned hyperspace.
4142
*/
4243
extern ChunkInsertState *
43-
chunk_dispatch_get_chunk_insert_state(ChunkDispatch *dispatch, Point *point)
44+
chunk_dispatch_get_chunk_insert_state(ChunkDispatch *dispatch, Point *point, CmdType operation)
4445
{
4546
ChunkInsertState *cis;
4647

@@ -55,7 +56,7 @@ chunk_dispatch_get_chunk_insert_state(ChunkDispatch *dispatch, Point *point)
5556
if (NULL == new_chunk)
5657
elog(ERROR, "No chunk found or created");
5758

58-
cis = chunk_insert_state_create(new_chunk, dispatch);
59+
cis = chunk_insert_state_create(new_chunk, dispatch, operation);
5960
subspace_store_add(dispatch->cache, new_chunk->cube, cis, destroy_chunk_insert_state);
6061
}
6162

0 commit comments

Comments
 (0)