Skip to content

Commit

Permalink
Fix telemetry test when compiled without SSL support
Browse files Browse the repository at this point in the history
The telemetry test failed with a missing SSL support error when there
was no SSL support compiled into the extension. This change
transparently uses plain connections in case of no SSL support so that
the test doesn't fail with an SSL-specific error.

A minor bug is also fixed in `plain_connect()`. This bug caused the
function to return success in case of name resolution errors. This was
in most cases harmless since the subsequent connect would fail in any
case.
  • Loading branch information
erimatnor committed Oct 3, 2018
1 parent bff0d4e commit 65817c8
Show file tree
Hide file tree
Showing 5 changed files with 43 additions and 36 deletions.
15 changes: 15 additions & 0 deletions src/net/conn_plain.c
Original file line number Diff line number Diff line change
Expand Up @@ -50,7 +50,22 @@ plain_connect(Connection *conn, const char *host, const char *servname, int port
ret = getaddrinfo(host, servname, &hints, &ainfo);

if (ret != 0)
{
ret = SOCKET_ERROR;

#ifdef WIN32
WSASetLastError(WSAHOST_NOT_FOUND);
#else

/*
* The closest match for a name resolution error. Strictly, this error
* should not be used here, but to fix we need to support using
* gai_strerror()
*/
errno = EADDRNOTAVAIL;
#endif
goto out;
}

#ifdef WIN32

Expand Down
20 changes: 11 additions & 9 deletions src/telemetry/telemetry.c
Original file line number Diff line number Diff line change
Expand Up @@ -249,16 +249,21 @@ build_version_request(const char *host, const char *path)
Connection *
telemetry_connect(const char *host, const char *service)
{
Connection *conn;
Connection *conn = NULL;
int ret;

conn = connection_create(CONNECTION_SSL);
if (strcmp("http", service) == 0)
conn = connection_create(CONNECTION_PLAIN);
else if (strcmp("https", service) == 0)
conn = connection_create(CONNECTION_SSL);
else
ereport(WARNING,
(errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
errmsg("scheme \"%s\" not supported for telemetry",
service)));

if (conn == NULL)
{
elog(WARNING, "could not create telemetry connection");
return NULL;
}

ret = connection_connect(conn, host, service, 0);

Expand All @@ -271,7 +276,7 @@ telemetry_connect(const char *host, const char *service)

ereport(WARNING,
(errcode(ERRCODE_INTERNAL_ERROR),
errmsg("could not make a connection to %s://%s", service, host),
errmsg("telemetry could not connect to \"%s\"", host),
errdetail("%s", errstr)));
}

Expand Down Expand Up @@ -305,10 +310,7 @@ telemetry_main(const char *host, const char *path, const char *service)
conn = telemetry_connect(host, service);

if (conn == NULL)
{
elog(WARNING, "telemetry connect error: could not make connection");
goto cleanup;
}

req = build_version_request(host, path);

Expand Down
24 changes: 4 additions & 20 deletions test/expected/telemetry.out
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ CREATE OR REPLACE FUNCTION _timescaledb_internal.test_status_mock(text) RETURNS
CREATE OR REPLACE FUNCTION _timescaledb_internal.test_telemetry_parse_version(response text, installed_major int, installed_minor int, installed_patch int, installed_modtag text = NULL)
RETURNS TABLE(version_string text, major int, minor int, patch int, modtag text, up_to_date bool)
AS :MODULE_PATHNAME, 'ts_test_telemetry_parse_version' LANGUAGE C IMMUTABLE PARALLEL SAFE;
CREATE OR REPLACE FUNCTION _timescaledb_internal.test_telemetry_main_conn(text, text, text)
CREATE OR REPLACE FUNCTION _timescaledb_internal.test_telemetry_main_conn(text, text)
RETURNS BOOLEAN AS :MODULE_PATHNAME, 'ts_test_telemetry_main_conn' LANGUAGE C IMMUTABLE PARALLEL SAFE;
CREATE OR REPLACE FUNCTION _timescaledb_internal.test_telemetry(host text = NULL, servname text = NULL, port int = NULL) RETURNS JSONB AS :MODULE_PATHNAME, 'ts_test_telemetry' LANGUAGE C IMMUTABLE PARALLEL SAFE;
\c single :ROLE_DEFAULT_PERM_USER
Expand Down Expand Up @@ -262,25 +262,9 @@ SELECT * FROM _timescaledb_internal.test_telemetry_parse_version('{"current_time
ERROR: parsing failed for version string "1.0.0-xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzz"
\set ON_ERROR_STOP 1
SET timescaledb.telemetry_level=basic;
SELECT _timescaledb_internal.test_telemetry_main_conn('timescale.com', 'path', 'http');
WARNING: could not make a connection to http://timescale.com
WARNING: telemetry connect error: could not make connection
test_telemetry_main_conn
--------------------------
f
(1 row)

SELECT _timescaledb_internal.test_telemetry_main_conn('timescale.com', 'path', 'https');
WARNING: could not make a connection to https://timescale.com
WARNING: telemetry connect error: could not make connection
test_telemetry_main_conn
--------------------------
f
(1 row)

SELECT _timescaledb_internal.test_telemetry_main_conn('telemetry.timescale.com', 'path', 'http');
WARNING: could not make a connection to http://telemetry.timescale.com
WARNING: telemetry connect error: could not make connection
-- Connect to a bogus host and path to test error handling in telemetry_main()
SELECT _timescaledb_internal.test_telemetry_main_conn('noservice.timescale.com', 'path');
WARNING: telemetry could not connect to "noservice.timescale.com"
test_telemetry_main_conn
--------------------------
f
Expand Down
7 changes: 3 additions & 4 deletions test/sql/telemetry.sql
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,7 @@ CREATE OR REPLACE FUNCTION _timescaledb_internal.test_status_mock(text) RETURNS
CREATE OR REPLACE FUNCTION _timescaledb_internal.test_telemetry_parse_version(response text, installed_major int, installed_minor int, installed_patch int, installed_modtag text = NULL)
RETURNS TABLE(version_string text, major int, minor int, patch int, modtag text, up_to_date bool)
AS :MODULE_PATHNAME, 'ts_test_telemetry_parse_version' LANGUAGE C IMMUTABLE PARALLEL SAFE;
CREATE OR REPLACE FUNCTION _timescaledb_internal.test_telemetry_main_conn(text, text, text)
CREATE OR REPLACE FUNCTION _timescaledb_internal.test_telemetry_main_conn(text, text)
RETURNS BOOLEAN AS :MODULE_PATHNAME, 'ts_test_telemetry_main_conn' LANGUAGE C IMMUTABLE PARALLEL SAFE;
CREATE OR REPLACE FUNCTION _timescaledb_internal.test_telemetry(host text = NULL, servname text = NULL, port int = NULL) RETURNS JSONB AS :MODULE_PATHNAME, 'ts_test_telemetry' LANGUAGE C IMMUTABLE PARALLEL SAFE;

Expand Down Expand Up @@ -117,7 +117,6 @@ SELECT * FROM _timescaledb_internal.test_telemetry_parse_version('{"current_time
SELECT * FROM _timescaledb_internal.test_telemetry_parse_version('{"current_timescaledb_version": "1.0.0-xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyyzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzzz"}', 1, 0, 0, 'alpha2');
\set ON_ERROR_STOP 1
SET timescaledb.telemetry_level=basic;
SELECT _timescaledb_internal.test_telemetry_main_conn('timescale.com', 'path', 'http');
SELECT _timescaledb_internal.test_telemetry_main_conn('timescale.com', 'path', 'https');
SELECT _timescaledb_internal.test_telemetry_main_conn('telemetry.timescale.com', 'path', 'http');
-- Connect to a bogus host and path to test error handling in telemetry_main()
SELECT _timescaledb_internal.test_telemetry_main_conn('noservice.timescale.com', 'path');
SET timescaledb.telemetry_level=off;
13 changes: 10 additions & 3 deletions test/src/telemetry/test_telemetry.c
Original file line number Diff line number Diff line change
Expand Up @@ -194,15 +194,22 @@ ts_test_telemetry_parse_version(PG_FUNCTION_ARGS)
return HeapTupleGetDatum(tuple);
}

/* Try to get the telemetry function to handle errors. Never connect to the actual endpoint. Only test cases that will result in connection errors. */
/* Try to get the telemetry function to handle errors. Never connect to the
* actual endpoint. Only test cases that will result in connection errors. */
Datum
ts_test_telemetry_main_conn(PG_FUNCTION_ARGS)
{
text *host = PG_GETARG_TEXT_P(0);
text *path = PG_GETARG_TEXT_P(1);
text *service = PG_GETARG_TEXT_P(2);
const char *scheme;

PG_RETURN_BOOL(telemetry_main(text_to_cstring(host), text_to_cstring(path), text_to_cstring(service)));
#ifdef TS_USE_OPENSSL
scheme = "https";
#else
scheme = "http";
#endif

PG_RETURN_BOOL(telemetry_main(text_to_cstring(host), text_to_cstring(path), scheme));
}

Datum
Expand Down

0 comments on commit 65817c8

Please sign in to comment.