aboutsummaryrefslogtreecommitdiff
path: root/tests/conninfo
diff options
context:
space:
mode:
Diffstat (limited to 'tests/conninfo')
-rw-r--r--tests/conninfo/buildfile13
-rw-r--r--tests/conninfo/driver.c74
-rw-r--r--tests/conninfo/expected.out171
-rw-r--r--tests/conninfo/postgres_fe.h19
-rw-r--r--tests/conninfo/regress.in57
-rw-r--r--tests/conninfo/testscript5
-rw-r--r--tests/conninfo/uri-regress.c84
7 files changed, 423 insertions, 0 deletions
diff --git a/tests/conninfo/buildfile b/tests/conninfo/buildfile
new file mode 100644
index 0000000..3ba850b
--- /dev/null
+++ b/tests/conninfo/buildfile
@@ -0,0 +1,13 @@
+# file : tests/conninfo/buildfile
+# copyright : Copyright (c) 2016-2017 Code Synthesis Ltd
+# license : PostgreSQL License; see accompanying COPYRIGHT file
+
+# Here we reproduce the original libpq test. See the src/interfaces/libpq/test
+# directory of the original package for details.
+#
+import libs = libpq%lib{pq}
+
+exe{driver}: {h c}{* -uri-regress} $libs test{testscript} \
+ file{uri-regress.c regress.in expected.out}
+
+c.poptions =+ "-I$src_base"
diff --git a/tests/conninfo/driver.c b/tests/conninfo/driver.c
new file mode 100644
index 0000000..2ff1007
--- /dev/null
+++ b/tests/conninfo/driver.c
@@ -0,0 +1,74 @@
+/* file : tests/conninfo/driver.c
+ * copyright : Copyright (c) 2016-2017 Code Synthesis Ltd
+ * license : PostgreSQL License; see accompanying COPYRIGHT file
+ */
+
+/*
+ * Include the original package test and rename it's main() function to test()
+ * (see below for details).
+ */
+#define main test
+#include <uri-regress.c>
+#undef main
+
+/*
+ * Enable assertions.
+ */
+#ifdef NDEBUG
+# undef NDEBUG
+#endif
+
+#include <stdio.h>
+#include <assert.h>
+#include <string.h> /* strlen() */
+
+/*
+ * Usage: argv[0]
+ *
+ * Read connection info strings from STDIN and call original test main()
+ * function for each of them. The function prints the parsed connection info to
+ * stdout on success or error message to stderr on failure.
+ */
+int
+main (int argc, char* argv[])
+{
+ assert (argc == 1);
+
+ char s[1024];
+
+ while (fgets (s, sizeof(s), stdin) != NULL)
+ {
+ /*
+ * Print the conninfo string that will be tested.
+ */
+ printf ("trying %s", s);
+
+ /*
+ * Strip the newline character and make sure it is printed to stdout.
+ */
+ size_t n = strlen (s);
+ if (n != 0 && s[n - 1] == '\n')
+ s[n - 1] = '\0';
+ else
+ printf ("\n");
+
+ /*
+ * Make sure the output make sense if stderr is redirected to stdout (and
+ * vice versa).
+ */
+ fflush (stdout);
+
+ /*
+ * Run the test.
+ *
+ * Note that we need to print the trailing newline character ourselves.
+ */
+ char* args[] = {argv[0], s, NULL};
+ int r = test (2, args);
+
+ fprintf (r == 0 ? stdout : stderr, "\n");
+ fflush (r == 0 ? stdout : stderr);
+ }
+
+ return 0;
+}
diff --git a/tests/conninfo/expected.out b/tests/conninfo/expected.out
new file mode 100644
index 0000000..d375e82
--- /dev/null
+++ b/tests/conninfo/expected.out
@@ -0,0 +1,171 @@
+trying postgresql://uri-user:secret@host:12345/db
+user='uri-user' password='secret' dbname='db' host='host' port='12345' (inet)
+
+trying postgresql://uri-user@host:12345/db
+user='uri-user' dbname='db' host='host' port='12345' (inet)
+
+trying postgresql://uri-user@host/db
+user='uri-user' dbname='db' host='host' (inet)
+
+trying postgresql://host:12345/db
+dbname='db' host='host' port='12345' (inet)
+
+trying postgresql://host/db
+dbname='db' host='host' (inet)
+
+trying postgresql://uri-user@host:12345/
+user='uri-user' host='host' port='12345' (inet)
+
+trying postgresql://uri-user@host/
+user='uri-user' host='host' (inet)
+
+trying postgresql://uri-user@
+user='uri-user' (local)
+
+trying postgresql://host:12345/
+host='host' port='12345' (inet)
+
+trying postgresql://host:12345
+host='host' port='12345' (inet)
+
+trying postgresql://host/db
+dbname='db' host='host' (inet)
+
+trying postgresql://host/
+host='host' (inet)
+
+trying postgresql://host
+host='host' (inet)
+
+trying postgresql://
+(local)
+
+trying postgresql://?hostaddr=127.0.0.1
+hostaddr='127.0.0.1' (inet)
+
+trying postgresql://example.com?hostaddr=63.1.2.4
+host='example.com' hostaddr='63.1.2.4' (inet)
+
+trying postgresql://%68ost/
+host='host' (inet)
+
+trying postgresql://host/db?user=uri-user
+user='uri-user' dbname='db' host='host' (inet)
+
+trying postgresql://host/db?user=uri-user&port=12345
+user='uri-user' dbname='db' host='host' port='12345' (inet)
+
+trying postgresql://host/db?u%73er=someotheruser&port=12345
+user='someotheruser' dbname='db' host='host' port='12345' (inet)
+
+trying postgresql://host/db?u%7aer=someotheruser&port=12345
+uri-regress: invalid URI query parameter: "uzer"
+
+trying postgresql://host:12345?user=uri-user
+user='uri-user' host='host' port='12345' (inet)
+
+trying postgresql://host?user=uri-user
+user='uri-user' host='host' (inet)
+
+trying postgresql://host?
+host='host' (inet)
+
+trying postgresql://[::1]:12345/db
+dbname='db' host='::1' port='12345' (inet)
+
+trying postgresql://[::1]/db
+dbname='db' host='::1' (inet)
+
+trying postgresql://[2001:db8::1234]/
+host='2001:db8::1234' (inet)
+
+trying postgresql://[200z:db8::1234]/
+host='200z:db8::1234' (inet)
+
+trying postgresql://[::1]
+host='::1' (inet)
+
+trying postgres://
+(local)
+
+trying postgres:///
+(local)
+
+trying postgres:///db
+dbname='db' (local)
+
+trying postgres://uri-user@/db
+user='uri-user' dbname='db' (local)
+
+trying postgres://?host=/path/to/socket/dir
+host='/path/to/socket/dir' (local)
+
+trying postgresql://host?uzer=
+uri-regress: invalid URI query parameter: "uzer"
+
+trying postgre://
+uri-regress: missing "=" after "postgre://" in connection info string
+
+trying postgres://[::1
+uri-regress: end of string reached when looking for matching "]" in IPv6 host address in URI: "postgres://[::1"
+
+trying postgres://[]
+uri-regress: IPv6 host address may not be empty in URI: "postgres://[]"
+
+trying postgres://[::1]z
+uri-regress: unexpected character "z" at position 17 in URI (expected ":" or "/"): "postgres://[::1]z"
+
+trying postgresql://host?zzz
+uri-regress: missing key/value separator "=" in URI query parameter: "zzz"
+
+trying postgresql://host?value1&value2
+uri-regress: missing key/value separator "=" in URI query parameter: "value1"
+
+trying postgresql://host?key=key=value
+uri-regress: extra key/value separator "=" in URI query parameter: "key"
+
+trying postgres://host?dbname=%XXfoo
+uri-regress: invalid percent-encoded token: "%XXfoo"
+
+trying postgresql://a%00b
+uri-regress: forbidden value %00 in percent-encoded value: "a%00b"
+
+trying postgresql://%zz
+uri-regress: invalid percent-encoded token: "%zz"
+
+trying postgresql://%1
+uri-regress: invalid percent-encoded token: "%1"
+
+trying postgresql://%
+uri-regress: invalid percent-encoded token: "%"
+
+trying postgres://@host
+host='host' (inet)
+
+trying postgres://host:/
+host='host' (inet)
+
+trying postgres://:12345/
+port='12345' (local)
+
+trying postgres://otheruser@?host=/no/such/directory
+user='otheruser' host='/no/such/directory' (local)
+
+trying postgres://otheruser@/?host=/no/such/directory
+user='otheruser' host='/no/such/directory' (local)
+
+trying postgres://otheruser@:12345?host=/no/such/socket/path
+user='otheruser' host='/no/such/socket/path' port='12345' (local)
+
+trying postgres://otheruser@:12345/db?host=/path/to/socket
+user='otheruser' dbname='db' host='/path/to/socket' port='12345' (local)
+
+trying postgres://:12345/db?host=/path/to/socket
+dbname='db' host='/path/to/socket' port='12345' (local)
+
+trying postgres://:12345?host=/path/to/socket
+host='/path/to/socket' port='12345' (local)
+
+trying postgres://%2Fvar%2Flib%2Fpostgresql/dbname
+dbname='dbname' host='/var/lib/postgresql' (local)
+
diff --git a/tests/conninfo/postgres_fe.h b/tests/conninfo/postgres_fe.h
new file mode 100644
index 0000000..2a62d51
--- /dev/null
+++ b/tests/conninfo/postgres_fe.h
@@ -0,0 +1,19 @@
+/* file : tests/conninfo/postgres_fe.h
+ * copyright : Copyright (c) 2016-2017 Code Synthesis Ltd
+ * license : PostgreSQL License; see accompanying COPYRIGHT file
+ */
+
+/*
+ * The original uri-regress.c includes src/include/postgres_fe.h that is
+ * located in libpq/postgresql/ directory in our source tree. This file is not
+ * installed, so to keep the test as a subproject and be able to test against
+ * the installed libpq library we replace it with the header stub, containing
+ * the bare minimum that is required the test to compile.
+ */
+#ifndef TESTS_CONNINFO_POSTGRES_FE_H
+#define TESTS_CONNINFO_POSTGRES_FE_H
+
+#include <stdbool.h>
+#include <string.h>
+
+#endif /* TESTS_CONNINFO_POSTGRES_FE_H */
diff --git a/tests/conninfo/regress.in b/tests/conninfo/regress.in
new file mode 100644
index 0000000..de034f3
--- /dev/null
+++ b/tests/conninfo/regress.in
@@ -0,0 +1,57 @@
+postgresql://uri-user:secret@host:12345/db
+postgresql://uri-user@host:12345/db
+postgresql://uri-user@host/db
+postgresql://host:12345/db
+postgresql://host/db
+postgresql://uri-user@host:12345/
+postgresql://uri-user@host/
+postgresql://uri-user@
+postgresql://host:12345/
+postgresql://host:12345
+postgresql://host/db
+postgresql://host/
+postgresql://host
+postgresql://
+postgresql://?hostaddr=127.0.0.1
+postgresql://example.com?hostaddr=63.1.2.4
+postgresql://%68ost/
+postgresql://host/db?user=uri-user
+postgresql://host/db?user=uri-user&port=12345
+postgresql://host/db?u%73er=someotheruser&port=12345
+postgresql://host/db?u%7aer=someotheruser&port=12345
+postgresql://host:12345?user=uri-user
+postgresql://host?user=uri-user
+postgresql://host?
+postgresql://[::1]:12345/db
+postgresql://[::1]/db
+postgresql://[2001:db8::1234]/
+postgresql://[200z:db8::1234]/
+postgresql://[::1]
+postgres://
+postgres:///
+postgres:///db
+postgres://uri-user@/db
+postgres://?host=/path/to/socket/dir
+postgresql://host?uzer=
+postgre://
+postgres://[::1
+postgres://[]
+postgres://[::1]z
+postgresql://host?zzz
+postgresql://host?value1&value2
+postgresql://host?key=key=value
+postgres://host?dbname=%XXfoo
+postgresql://a%00b
+postgresql://%zz
+postgresql://%1
+postgresql://%
+postgres://@host
+postgres://host:/
+postgres://:12345/
+postgres://otheruser@?host=/no/such/directory
+postgres://otheruser@/?host=/no/such/directory
+postgres://otheruser@:12345?host=/no/such/socket/path
+postgres://otheruser@:12345/db?host=/path/to/socket
+postgres://:12345/db?host=/path/to/socket
+postgres://:12345?host=/path/to/socket
+postgres://%2Fvar%2Flib%2Fpostgresql/dbname
diff --git a/tests/conninfo/testscript b/tests/conninfo/testscript
new file mode 100644
index 0000000..9853029
--- /dev/null
+++ b/tests/conninfo/testscript
@@ -0,0 +1,5 @@
+# file : tests/conninfo/testscript
+# copyright : Copyright (c) 2016-2017 Code Synthesis Ltd
+# license : PostgreSQL License; see accompanying COPYRIGHT file
+
+$* <<<$src_base/regress.in >>>$src_base/expected.out 2>&1
diff --git a/tests/conninfo/uri-regress.c b/tests/conninfo/uri-regress.c
new file mode 100644
index 0000000..bf1d970
--- /dev/null
+++ b/tests/conninfo/uri-regress.c
@@ -0,0 +1,84 @@
+/*
+ * uri-regress.c
+ * A test program for libpq URI format
+ *
+ * This is a helper for libpq conninfo regression testing. It takes a single
+ * conninfo string as a parameter, parses it using PQconninfoParse, and then
+ * prints out the values from the parsed PQconninfoOption struct that differ
+ * from the defaults (obtained from PQconndefaults).
+ *
+ * Portions Copyright (c) 2012-2016, PostgreSQL Global Development Group
+ *
+ * IDENTIFICATION
+ * src/interfaces/libpq/test/uri-regress.c
+ */
+
+#include "postgres_fe.h"
+
+#include "libpq-fe.h"
+
+int
+main(int argc, char *argv[])
+{
+ PQconninfoOption *opts;
+ PQconninfoOption *defs;
+ PQconninfoOption *opt;
+ PQconninfoOption *def;
+ char *errmsg = NULL;
+ bool local = true;
+
+ if (argc != 2)
+ return 1;
+
+ opts = PQconninfoParse(argv[1], &errmsg);
+ if (opts == NULL)
+ {
+ fprintf(stderr, "uri-regress: %s", errmsg);
+ return 1;
+ }
+
+ defs = PQconndefaults();
+ if (defs == NULL)
+ {
+ fprintf(stderr, "uri-regress: cannot fetch default options\n");
+ return 1;
+ }
+
+ /*
+ * Loop on the options, and print the value of each if not the default.
+ *
+ * XXX this coding assumes that PQconninfoOption structs always have the
+ * keywords in the same order.
+ */
+ for (opt = opts, def = defs; opt->keyword; ++opt, ++def)
+ {
+ if (opt->val != NULL)
+ {
+ if (def->val == NULL || strcmp(opt->val, def->val) != 0)
+ printf("%s='%s' ", opt->keyword, opt->val);
+
+ /*
+ * Try to detect if this is a Unix-domain socket or inet. This is
+ * a bit grotty but it's the same thing that libpq itself does.
+ *
+ * Note that we directly test for '/' instead of using
+ * is_absolute_path, as that would be considerably more messy.
+ * This would fail on Windows, but that platform doesn't have
+ * Unix-domain sockets anyway.
+ */
+ if (*opt->val &&
+ (strcmp(opt->keyword, "hostaddr") == 0 ||
+ (strcmp(opt->keyword, "host") == 0 && *opt->val != '/')))
+ {
+ local = false;
+ }
+ }
+ }
+
+ if (local)
+ printf("(local)\n");
+ else
+ printf("(inet)\n");
+
+ return 0;
+}