Change uri_path to return text
This commit is contained in:
parent
53789ec067
commit
527cc23bc4
13
README.md
13
README.md
|
@ -88,6 +88,19 @@ A number of functions are provided to extract parts of a URI:
|
||||||
Extracts the port of a URI as an integer, for example `5432`. If
|
Extracts the port of a URI as an integer, for example `5432`. If
|
||||||
no port is specified, the return value is null.
|
no port is specified, the return value is null.
|
||||||
|
|
||||||
|
- `uri_path(uri) returns text`
|
||||||
|
|
||||||
|
Extracts the path component of a URI. Logically, a URI always
|
||||||
|
contains a path. The return value can be an empty string but
|
||||||
|
never null.
|
||||||
|
|
||||||
|
- `uri_path_array(uri) returns text[]`
|
||||||
|
|
||||||
|
Returns the path component of a URI as an array, with the path
|
||||||
|
split at the slash characters. This is probably not as useful as
|
||||||
|
the `uri_path` function, but it is provided here because the
|
||||||
|
`uriparser` library exposes it.
|
||||||
|
|
||||||
- `uri_query(uri) returns text`
|
- `uri_query(uri) returns text`
|
||||||
|
|
||||||
Extracts the query part of a URI (roughly speaking, everything
|
Extracts the query part of a URI (roughly speaking, everything
|
||||||
|
|
|
@ -13,7 +13,9 @@ VALUES ('http://www.postgresql.org/'),
|
||||||
('http://[1080::8:800:200C:417A]/foo'),
|
('http://[1080::8:800:200C:417A]/foo'),
|
||||||
('http://host:'),
|
('http://host:'),
|
||||||
(''),
|
(''),
|
||||||
('foobar');
|
('/'),
|
||||||
|
('foobar'),
|
||||||
|
('/foobar');
|
||||||
SELECT * FROM test;
|
SELECT * FROM test;
|
||||||
a | b
|
a | b
|
||||||
----+-----------------------------------------------------------------------------------------
|
----+-----------------------------------------------------------------------------------------
|
||||||
|
@ -28,8 +30,10 @@ SELECT * FROM test;
|
||||||
9 | http://[1080::8:800:200C:417A]/foo
|
9 | http://[1080::8:800:200C:417A]/foo
|
||||||
10 | http://host:
|
10 | http://host:
|
||||||
11 |
|
11 |
|
||||||
12 | foobar
|
12 | /
|
||||||
(12 rows)
|
13 | foobar
|
||||||
|
14 | /foobar
|
||||||
|
(14 rows)
|
||||||
|
|
||||||
-- error cases
|
-- error cases
|
||||||
SELECT uri 'http://host:port/';
|
SELECT uri 'http://host:port/';
|
||||||
|
@ -44,127 +48,162 @@ SELECT b AS uri,
|
||||||
uri_host_inet(b),
|
uri_host_inet(b),
|
||||||
uri_port(b),
|
uri_port(b),
|
||||||
uri_path(b),
|
uri_path(b),
|
||||||
|
uri_path_array(b),
|
||||||
uri_query(b),
|
uri_query(b),
|
||||||
uri_fragment(b)
|
uri_fragment(b)
|
||||||
FROM test;
|
FROM test;
|
||||||
-[ RECORD 1 ]-+----------------------------------------------------------------------------------------
|
-[ RECORD 1 ]--+----------------------------------------------------------------------------------------
|
||||||
uri | http://www.postgresql.org/
|
uri | http://www.postgresql.org/
|
||||||
uri_scheme | http
|
uri_scheme | http
|
||||||
uri_userinfo | _null_
|
uri_userinfo | _null_
|
||||||
uri_host | www.postgresql.org
|
uri_host | www.postgresql.org
|
||||||
uri_host_inet | _null_
|
uri_host_inet | _null_
|
||||||
uri_port | _null_
|
uri_port | _null_
|
||||||
uri_path | {""}
|
uri_path | /
|
||||||
|
uri_path_array | {""}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
-[ RECORD 2 ]-+----------------------------------------------------------------------------------------
|
-[ RECORD 2 ]--+----------------------------------------------------------------------------------------
|
||||||
uri | http://www.postgresql.org/docs/devel/static/xfunc-sql.html#XFUNC-SQL-FUNCTION-ARGUMENTS
|
uri | http://www.postgresql.org/docs/devel/static/xfunc-sql.html#XFUNC-SQL-FUNCTION-ARGUMENTS
|
||||||
uri_scheme | http
|
uri_scheme | http
|
||||||
uri_userinfo | _null_
|
uri_userinfo | _null_
|
||||||
uri_host | www.postgresql.org
|
uri_host | www.postgresql.org
|
||||||
uri_host_inet | _null_
|
uri_host_inet | _null_
|
||||||
uri_port | _null_
|
uri_port | _null_
|
||||||
uri_path | {docs,devel,static,xfunc-sql.html}
|
uri_path | /docs/devel/static/xfunc-sql.html
|
||||||
|
uri_path_array | {docs,devel,static,xfunc-sql.html}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | XFUNC-SQL-FUNCTION-ARGUMENTS
|
uri_fragment | XFUNC-SQL-FUNCTION-ARGUMENTS
|
||||||
-[ RECORD 3 ]-+----------------------------------------------------------------------------------------
|
-[ RECORD 3 ]--+----------------------------------------------------------------------------------------
|
||||||
uri | https://duckduckgo.com/?q=postgresql&ia=about
|
uri | https://duckduckgo.com/?q=postgresql&ia=about
|
||||||
uri_scheme | https
|
uri_scheme | https
|
||||||
uri_userinfo | _null_
|
uri_userinfo | _null_
|
||||||
uri_host | duckduckgo.com
|
uri_host | duckduckgo.com
|
||||||
uri_host_inet | _null_
|
uri_host_inet | _null_
|
||||||
uri_port | _null_
|
uri_port | _null_
|
||||||
uri_path | {""}
|
uri_path | /
|
||||||
|
uri_path_array | {""}
|
||||||
uri_query | q=postgresql&ia=about
|
uri_query | q=postgresql&ia=about
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
-[ RECORD 4 ]-+----------------------------------------------------------------------------------------
|
-[ RECORD 4 ]--+----------------------------------------------------------------------------------------
|
||||||
uri | ftp://ftp.gnu.org/gnu/bison
|
uri | ftp://ftp.gnu.org/gnu/bison
|
||||||
uri_scheme | ftp
|
uri_scheme | ftp
|
||||||
uri_userinfo | _null_
|
uri_userinfo | _null_
|
||||||
uri_host | ftp.gnu.org
|
uri_host | ftp.gnu.org
|
||||||
uri_host_inet | _null_
|
uri_host_inet | _null_
|
||||||
uri_port | _null_
|
uri_port | _null_
|
||||||
uri_path | {gnu,bison}
|
uri_path | /gnu/bison
|
||||||
|
uri_path_array | {gnu,bison}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
-[ RECORD 5 ]-+----------------------------------------------------------------------------------------
|
-[ RECORD 5 ]--+----------------------------------------------------------------------------------------
|
||||||
uri | mailto:foo@example.com
|
uri | mailto:foo@example.com
|
||||||
uri_scheme | mailto
|
uri_scheme | mailto
|
||||||
uri_userinfo | _null_
|
uri_userinfo | _null_
|
||||||
uri_host | _null_
|
uri_host | _null_
|
||||||
uri_host_inet | _null_
|
uri_host_inet | _null_
|
||||||
uri_port | _null_
|
uri_port | _null_
|
||||||
uri_path | {foo@example.com}
|
uri_path | foo@example.com
|
||||||
|
uri_path_array | {foo@example.com}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
-[ RECORD 6 ]-+----------------------------------------------------------------------------------------
|
-[ RECORD 6 ]--+----------------------------------------------------------------------------------------
|
||||||
uri | ssh://username@review.openstack.org:29418/openstack/nova.git
|
uri | ssh://username@review.openstack.org:29418/openstack/nova.git
|
||||||
uri_scheme | ssh
|
uri_scheme | ssh
|
||||||
uri_userinfo | username
|
uri_userinfo | username
|
||||||
uri_host | review.openstack.org
|
uri_host | review.openstack.org
|
||||||
uri_host_inet | _null_
|
uri_host_inet | _null_
|
||||||
uri_port | 29418
|
uri_port | 29418
|
||||||
uri_path | {openstack,nova.git}
|
uri_path | /openstack/nova.git
|
||||||
|
uri_path_array | {openstack,nova.git}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
-[ RECORD 7 ]-+----------------------------------------------------------------------------------------
|
-[ RECORD 7 ]--+----------------------------------------------------------------------------------------
|
||||||
uri | http://admin:password@192.168.0.1
|
uri | http://admin:password@192.168.0.1
|
||||||
uri_scheme | http
|
uri_scheme | http
|
||||||
uri_userinfo | admin:password
|
uri_userinfo | admin:password
|
||||||
uri_host | 192.168.0.1
|
uri_host | 192.168.0.1
|
||||||
uri_host_inet | 192.168.0.1
|
uri_host_inet | 192.168.0.1
|
||||||
uri_port | _null_
|
uri_port | _null_
|
||||||
uri_path | {}
|
uri_path |
|
||||||
|
uri_path_array | {}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
-[ RECORD 8 ]-+----------------------------------------------------------------------------------------
|
-[ RECORD 8 ]--+----------------------------------------------------------------------------------------
|
||||||
uri | http://[FEDC:BA98:7654:3210:FEDC:BA98:7654:3210]:80/index.html
|
uri | http://[FEDC:BA98:7654:3210:FEDC:BA98:7654:3210]:80/index.html
|
||||||
uri_scheme | http
|
uri_scheme | http
|
||||||
uri_userinfo | _null_
|
uri_userinfo | _null_
|
||||||
uri_host | FEDC:BA98:7654:3210:FEDC:BA98:7654:3210
|
uri_host | FEDC:BA98:7654:3210:FEDC:BA98:7654:3210
|
||||||
uri_host_inet | fedc:ba98:7654:3210:fedc:ba98:7654:3210
|
uri_host_inet | fedc:ba98:7654:3210:fedc:ba98:7654:3210
|
||||||
uri_port | 80
|
uri_port | 80
|
||||||
uri_path | {index.html}
|
uri_path | /index.html
|
||||||
|
uri_path_array | {index.html}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
-[ RECORD 9 ]-+----------------------------------------------------------------------------------------
|
-[ RECORD 9 ]--+----------------------------------------------------------------------------------------
|
||||||
uri | http://[1080::8:800:200C:417A]/foo
|
uri | http://[1080::8:800:200C:417A]/foo
|
||||||
uri_scheme | http
|
uri_scheme | http
|
||||||
uri_userinfo | _null_
|
uri_userinfo | _null_
|
||||||
uri_host | 1080::8:800:200C:417A
|
uri_host | 1080::8:800:200C:417A
|
||||||
uri_host_inet | 1080::8:800:200c:417a
|
uri_host_inet | 1080::8:800:200c:417a
|
||||||
uri_port | _null_
|
uri_port | _null_
|
||||||
uri_path | {foo}
|
uri_path | /foo
|
||||||
|
uri_path_array | {foo}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
-[ RECORD 10 ]+----------------------------------------------------------------------------------------
|
-[ RECORD 10 ]-+----------------------------------------------------------------------------------------
|
||||||
uri | http://host:
|
uri | http://host:
|
||||||
uri_scheme | http
|
uri_scheme | http
|
||||||
uri_userinfo | _null_
|
uri_userinfo | _null_
|
||||||
uri_host | host
|
uri_host | host
|
||||||
uri_host_inet | _null_
|
uri_host_inet | _null_
|
||||||
uri_port | _null_
|
uri_port | _null_
|
||||||
uri_path | {}
|
uri_path |
|
||||||
|
uri_path_array | {}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
-[ RECORD 11 ]+----------------------------------------------------------------------------------------
|
-[ RECORD 11 ]-+----------------------------------------------------------------------------------------
|
||||||
uri |
|
uri |
|
||||||
uri_scheme | _null_
|
uri_scheme | _null_
|
||||||
uri_userinfo | _null_
|
uri_userinfo | _null_
|
||||||
uri_host | _null_
|
uri_host | _null_
|
||||||
uri_host_inet | _null_
|
uri_host_inet | _null_
|
||||||
uri_port | _null_
|
uri_port | _null_
|
||||||
uri_path | {}
|
uri_path |
|
||||||
|
uri_path_array | {}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
-[ RECORD 12 ]+----------------------------------------------------------------------------------------
|
-[ RECORD 12 ]-+----------------------------------------------------------------------------------------
|
||||||
|
uri | /
|
||||||
|
uri_scheme | _null_
|
||||||
|
uri_userinfo | _null_
|
||||||
|
uri_host | _null_
|
||||||
|
uri_host_inet | _null_
|
||||||
|
uri_port | _null_
|
||||||
|
uri_path | /
|
||||||
|
uri_path_array | {}
|
||||||
|
uri_query | _null_
|
||||||
|
uri_fragment | _null_
|
||||||
|
-[ RECORD 13 ]-+----------------------------------------------------------------------------------------
|
||||||
uri | foobar
|
uri | foobar
|
||||||
uri_scheme | _null_
|
uri_scheme | _null_
|
||||||
uri_userinfo | _null_
|
uri_userinfo | _null_
|
||||||
uri_host | _null_
|
uri_host | _null_
|
||||||
uri_host_inet | _null_
|
uri_host_inet | _null_
|
||||||
uri_port | _null_
|
uri_port | _null_
|
||||||
uri_path | {foobar}
|
uri_path | foobar
|
||||||
|
uri_path_array | {foobar}
|
||||||
|
uri_query | _null_
|
||||||
|
uri_fragment | _null_
|
||||||
|
-[ RECORD 14 ]-+----------------------------------------------------------------------------------------
|
||||||
|
uri | /foobar
|
||||||
|
uri_scheme | _null_
|
||||||
|
uri_userinfo | _null_
|
||||||
|
uri_host | _null_
|
||||||
|
uri_host_inet | _null_
|
||||||
|
uri_port | _null_
|
||||||
|
uri_path | /foobar
|
||||||
|
uri_path_array | {foobar}
|
||||||
uri_query | _null_
|
uri_query | _null_
|
||||||
uri_fragment | _null_
|
uri_fragment | _null_
|
||||||
|
|
||||||
|
@ -173,6 +212,8 @@ SELECT DISTINCT b FROM test ORDER BY b;
|
||||||
b
|
b
|
||||||
-----------------------------------------------------------------------------------------
|
-----------------------------------------------------------------------------------------
|
||||||
|
|
||||||
|
/
|
||||||
|
/foobar
|
||||||
foobar
|
foobar
|
||||||
ftp://ftp.gnu.org/gnu/bison
|
ftp://ftp.gnu.org/gnu/bison
|
||||||
http://[1080::8:800:200C:417A]/foo
|
http://[1080::8:800:200C:417A]/foo
|
||||||
|
@ -184,5 +225,5 @@ SELECT DISTINCT b FROM test ORDER BY b;
|
||||||
https://duckduckgo.com/?q=postgresql&ia=about
|
https://duckduckgo.com/?q=postgresql&ia=about
|
||||||
mailto:foo@example.com
|
mailto:foo@example.com
|
||||||
ssh://username@review.openstack.org:29418/openstack/nova.git
|
ssh://username@review.openstack.org:29418/openstack/nova.git
|
||||||
(12 rows)
|
(14 rows)
|
||||||
|
|
||||||
|
|
|
@ -16,7 +16,9 @@ VALUES ('http://www.postgresql.org/'),
|
||||||
('http://[1080::8:800:200C:417A]/foo'),
|
('http://[1080::8:800:200C:417A]/foo'),
|
||||||
('http://host:'),
|
('http://host:'),
|
||||||
(''),
|
(''),
|
||||||
('foobar');
|
('/'),
|
||||||
|
('foobar'),
|
||||||
|
('/foobar');
|
||||||
|
|
||||||
SELECT * FROM test;
|
SELECT * FROM test;
|
||||||
|
|
||||||
|
@ -32,6 +34,7 @@ SELECT b AS uri,
|
||||||
uri_host_inet(b),
|
uri_host_inet(b),
|
||||||
uri_port(b),
|
uri_port(b),
|
||||||
uri_path(b),
|
uri_path(b),
|
||||||
|
uri_path_array(b),
|
||||||
uri_query(b),
|
uri_query(b),
|
||||||
uri_fragment(b)
|
uri_fragment(b)
|
||||||
FROM test;
|
FROM test;
|
||||||
|
|
29
uri.c
29
uri.c
|
@ -1,6 +1,7 @@
|
||||||
#include <postgres.h>
|
#include <postgres.h>
|
||||||
#include <catalog/pg_type.h>
|
#include <catalog/pg_type.h>
|
||||||
#include <fmgr.h>
|
#include <fmgr.h>
|
||||||
|
#include <lib/stringinfo.h>
|
||||||
#include <utils/array.h>
|
#include <utils/array.h>
|
||||||
#include <utils/builtins.h>
|
#include <utils/builtins.h>
|
||||||
#include <utils/inet.h>
|
#include <utils/inet.h>
|
||||||
|
@ -223,6 +224,34 @@ uri_fragment(PG_FUNCTION_ARGS)
|
||||||
PG_FUNCTION_INFO_V1(uri_path);
|
PG_FUNCTION_INFO_V1(uri_path);
|
||||||
Datum
|
Datum
|
||||||
uri_path(PG_FUNCTION_ARGS)
|
uri_path(PG_FUNCTION_ARGS)
|
||||||
|
{
|
||||||
|
Datum arg = PG_GETARG_DATUM(0);
|
||||||
|
char *s = TextDatumGetCString(arg);
|
||||||
|
UriUriA uri;
|
||||||
|
StringInfoData buf;
|
||||||
|
UriPathSegmentA *p;
|
||||||
|
|
||||||
|
initStringInfo(&buf);
|
||||||
|
|
||||||
|
parse_uri(s, &uri);
|
||||||
|
|
||||||
|
if (uri.absolutePath || (uriIsHostSetA(&uri) && uri.pathHead))
|
||||||
|
appendStringInfoChar(&buf, '/');
|
||||||
|
|
||||||
|
for (p = uri.pathHead; p; p = p->next)
|
||||||
|
{
|
||||||
|
appendBinaryStringInfo(&buf, p->text.first, p->text.afterLast - p->text.first);
|
||||||
|
if (p->next)
|
||||||
|
appendStringInfoChar(&buf, '/');
|
||||||
|
}
|
||||||
|
|
||||||
|
uriFreeUriMembersA(&uri);
|
||||||
|
PG_RETURN_TEXT_P(cstring_to_text(buf.data));
|
||||||
|
}
|
||||||
|
|
||||||
|
PG_FUNCTION_INFO_V1(uri_path_array);
|
||||||
|
Datum
|
||||||
|
uri_path_array(PG_FUNCTION_ARGS)
|
||||||
{
|
{
|
||||||
Datum arg = PG_GETARG_DATUM(0);
|
Datum arg = PG_GETARG_DATUM(0);
|
||||||
char *s = TextDatumGetCString(arg);
|
char *s = TextDatumGetCString(arg);
|
||||||
|
|
8
uri.sql
8
uri.sql
|
@ -68,7 +68,13 @@ CREATE FUNCTION uri_fragment(uri) RETURNS text
|
||||||
LANGUAGE C
|
LANGUAGE C
|
||||||
AS '$libdir/uri';
|
AS '$libdir/uri';
|
||||||
|
|
||||||
CREATE FUNCTION uri_path(uri) RETURNS text[]
|
CREATE FUNCTION uri_path(uri) RETURNS text
|
||||||
|
IMMUTABLE
|
||||||
|
STRICT
|
||||||
|
LANGUAGE C
|
||||||
|
AS '$libdir/uri';
|
||||||
|
|
||||||
|
CREATE FUNCTION uri_path_array(uri) RETURNS text[]
|
||||||
IMMUTABLE
|
IMMUTABLE
|
||||||
STRICT
|
STRICT
|
||||||
LANGUAGE C
|
LANGUAGE C
|
||||||
|
|
Loading…
Reference in New Issue