Re: Gestion des adresses URL avec parse_url

From: Samuel ROZE <samuel(dot)roze(at)gmail(dot)com>
To: pgsql-fr-generale(at)postgresql(dot)org
Subject: Re: Gestion des adresses URL avec parse_url
Date: 2009-10-22 23:11:27
Message-ID: 1256253087.2744.4.camel@samuel-laptop
Views: Raw Message | Whole Thread | Download mbox | Resend email
Thread:
Lists: pgsql-fr-generale

Il s'avère qu'il y a un bug lors de la création de tables avec le type
"url" que je ne voit pas comment résoudre... Pourriez-vous m'apporter
vos lumières ? :/

---------------------------------------------------------
postgres=# CREATE TABLE tests_url (
postgres(# id SERIAL,
postgres(# mon_url url,
postgres(# url_text text
postgres(# );
NOTICE: CREATE TABLE will create implicit sequence "tests_url_id_seq" for serial column "tests_url.id"
CREATE TABLE
postgres=# INSERT INTO tests_url (mon_url) VALUES ('http://www.postgresqlfr.org');
server closed the connection unexpectedly
This probably means the server terminated abnormally
before or while processing the request.
The connection to the server was lost. Attempting reset: Succeeded.
---------------------------------------------------------

Si en même temps j'utilise gdb et qu'après le crash je fait un
backtrace, voilà ce que j'ai:
---------------------------------------------------------
Program received signal SIGSEGV, Segmentation fault.
0xb7dd0b56 in memcpy () from /lib/tls/i686/cmov/libc.so.6
(gdb) bt
#0 0xb7dd0b56 in memcpy () from /lib/tls/i686/cmov/libc.so.6
#1 0x00000001 in ?? ()
#2 0x080906b5 in heap_form_tuple (tupleDescriptor=0x8686020, values=0x8686228, isnull=0x86862d0 "") at heaptuple.c:757
#3 0x0819b879 in ExecCopySlotTuple (slot=0x84efa5) at execTuples.c:641
#4 0x0819b8b2 in ExecMaterializeSlot (slot=0x8685590) at execTuples.c:833
#5 0x0819156b in standard_ExecutorRun (queryDesc=0x8684fc8, direction=ForwardScanDirection, count=0) at execMain.c:1761
#6 0x08242a26 in ProcessQuery (plan=0x863f508, sourceText=0x863df10 "INSERT INTO tests_url (mon_url) VALUES ('http://www.postgresqlfr.org');",
params=<value optimized out>, dest=0x863f798, completionTag=0xbfc0a478 "") at pquery.c:196
#7 0x08242c2b in PortalRunMulti (portal=0x8682fc0, isTopLevel=<value optimized out>, dest=0x863f798, altdest=0x863f798, completionTag=0xbfc0a478 "")
at pquery.c:1269
#8 0x082433a4 in PortalRun (portal=0x8682fc0, count=2147483647, isTopLevel=-116 '\214', dest=0x863f798, altdest=0x863f798, completionTag=0xbfc0a478 "")
at pquery.c:823
#9 0x0823e1a8 in exec_simple_query (query_string=0x863df10 "INSERT INTO tests_url (mon_url) VALUES ('http://www.postgresqlfr.org');") at postgres.c:991
#10 0x0823fadf in PostgresMain (argc=4, argv=0x85cb208, username=0x85cb1d8 "postgres") at postgres.c:3614
#11 0x0821237b in ServerLoop () at postmaster.c:3447
#12 0x0821339a in PostmasterMain (argc=3, argv=0x85c71d0) at postmaster.c:1040
#13 0x081bb936 in main (argc=3, argv=0x85c71d0) at main.c:188
---------------------------------------------------------

Un problème de mémoire... Ce que je ne comprend pas c'est pourquoi ça
marche dans les autres cas et pas là.. Bizarre ! J'ai chercher
différentes variables qui auraient pu être non-initialisées mais je ne
voit pas...

Merci d'avance !
Samuel.

Le vendredi 23 octobre 2009 à 00:59 +0200, Samuel ROZE a écrit :
> Bonjour !
>
> Tout d'abord, merci beaucoup pour l'attention que vous porter à mon
> petit projet.
>
> J'ai grandement modifier le code source dans cette "v2", qui ne
> s'appelle déjà plus "parse_url" mais "url" (même si la fonction
> "parse_url" a toujours le même nom).
>
> J'ai créer:
> - Un type interne "urltype" à la place de l'ancien type "url"
> - Un type SQL "url" défini par les deux fonctions suivantes:
> - Une fonction "url_in" et son homologue "url_out" pour gérer le type de
> donnée "url".
> - Un type SQL "url_record", retourné par "parse_url(url)"
>
> http://www.d-sites.com/wp-content/uploads/2009/10/url.tar.gz
>
> Comme avant, il est compilable par un simple "make" et les requêtes SQL
> à exécuter sont présentes dans le fichier "url.sql".
>
> Voici quelques exemples:
> postgres=# SELECT parse_url('http://www.d-sites.com/index.php?q=query&r=postgresql#p2');
> parse_url
> --------------------------------------------------------------
> (http,,,www.d-sites.com,,/index.php,q=query&r=postgresql,p2)
> (1 row)
>
> postgres=# SELECT * FROM parse_url('http://www.d-sites.com/index.php?q=query&r=postgresql#p2');
> scheme | user | pass | host | port | path | query | fragment
> --------+------+------+-----------------+------+------------+----------------------+----------
> http | | | www.d-sites.com | | /index.php | q=query&r=postgresql | p2
> (1 row)
>
> postgres=# SELECT parse_url('http://www.d-sites.com/index.php?q=query&r=postgresql#p2', 'query');
> parse_url
> ----------------------
> q=query&r=postgresql
> (1 row)
>
> Toujours le même chose, qu'en pensez-vous ?
>
> Merci encore !
> Cordialement,
> Samuel.
>
> Le mercredi 21 octobre 2009 à 22:00 +0200, Samuel ROZE a écrit :
> > Bonjour à tous,
> >
> > Je viens ici demander quelques feedbacks à propos d'une fonctionnalité
> > que je suis en train de développer.
> >
> > Je suis en train de développer une série de fonctions permettant de
> > manipuler des adresses URL directement dans la base de données. Pour le
> > moment, j'ai fait le plus dur avec ces fonctions:
> > - url *parse_url_exec (char * url_str) - utilisée par les deux
> > fonctions suivantes
> > - Datum parse_url_key (PG_FUNCTION_ARGS) qui prend deux arguments:
> > - text: L'adresse URL
> > - text: Quoi récupérer dans cette liste: scheme (http, https, ftp,
> > etc...), user (le nom d'utilisateur quand il y a), pass (mot de passe
> > quand il y a), host (nom de domaine), path, query (requête - i.e. après
> > "?"), fragment (quel endroit de la page - i.e. après "#")
> > - Datum parse_url_record (PG_FUNCTION_ARGS) qui prend un seul argument
> > (text), l'adresse URL. Elle retourne un tuple de char*. i.e. un record.
> >
> > Pour simplifier la vie pour la récupération du record, j'ai fait un type
> > SQL "url" comme ceci:
> > ------------------------------------------------------------
> > CREATE TYPE url AS ("scheme" text, "user" text, "pass" text, "host"
> > text, "port" integer, "path" text, "query" text, "fragment" text);
> > ------------------------------------------------------------
> >
> > Les deux fonctions C sont définies comme ça:
> > ------------------------------------------------------------
> > CREATE FUNCTION parse_url(text, text) RETURNS text AS 'parse_url.so',
> > 'parse_url_key' LANGUAGE C STRICT;
> > ------------------------------------------------------------
> > CREATE FUNCTION parse_url (text) RETURNS url AS 'parse_url.so',
> > 'parse_url_record' LANGUAGE C STRICT;
> > ------------------------------------------------------------
> >
> > Vous pouvez télécharger le code dans une archive contenant le fichier .c
> > et .h, le Makefile ainsi que un fichier SQL qui contient ce que je vous
> > ai présenté ci-dessus.
> > http://www.d-sites.com/wp-content/uploads/2009/10/parse_url.tar.gz
> >
> > En toute logique, je vais continuer pour créer un "vrai" type de donnée
> > "url" utilisable en tant que champ SQL, qui permettra ensuite de bien
> > mieux gérer les adresses URL.
> >
> > Je souhaites avoir des retours de votre part avant d'en faire part à la
> > mailing "pgsql-hackers@" ainsi qu'avant publication sur mon blog.
> >
> > Note: cf en bas du mail pour les résultats de quelques requêtes sur ma
> > base de test en 8.4.1.
> >
> > Cordialement,
> > Samuel ROZE.
> > http://wwW.d-sites.com
> >
> > ------------------------------------------------------------
> > Sur une base de données PostgreSQL 8.4.1, avec le même code que dans
> > l'archive ci-dessus, compilé avec le même Makefile, après application
> > des 3 requêtes de création et type et de fonction, voilà le résultat
> > obtenu:
> >
> > postgres=# SELECT parse_url('http://www.d-sites.com/test.php?query=info', 'host');
> > parse_url
> > -----------------
> > www.d-sites.com
> > (1 row)
> >
> > postgres=# SELECT parse_url('http://www.d-sites.com/test.php?query=info', 'scheme');
> > parse_url
> > -----------
> > http
> > (1 row)
> >
> > postgres=# SELECT parse_url('http://www.d-sites.com/test.php?query=info', 'port');
> > parse_url
> > -----------
> >
> > (1 row)
> >
> > postgres=# SELECT parse_url('http://www.d-sites.com/test.php?query=info', 'port') IS NULL;
> > ?column?
> > ----------
> > t
> > (1 row)
> >
> > postgres=# SELECT * FROM parse_url('http://www.d-sites.com/test.php?query=info');
> > scheme | user | pass | host | port | path | query | fragment
> > --------+------+------+-----------------+------+-----------+------------+----------
> > http | | | www.d-sites.com | | /test.php | query=info |
> > (1 row)
> >
> > postgres=# SELECT * FROM parse_url('http://www.postgresql.org/docs/8.4/static/xfunc-c.html#AEN44968');
> > scheme | user | pass | host | port | path | query | fragment
> > --------+------+------+--------------------+------+-------------------------------+-------+----------
> > http | | | www.postgresql.org | | /docs/8.4/static/xfunc-c.html | | AEN44968
> > (1 row)
> >
> > postgres=# EXPLAIN ANALYSE SELECT * FROM parse_url('http://www.postgresql.org/docs/8.4/static/xfunc-c.html#AEN44968');
> > QUERY PLAN
> > -----------------------------------------------------------------------------------------------------------
> > Function Scan on parse_url (cost=0.00..0.01 rows=1 width=228) (actual time=0.036..0.039 rows=1 loops=1)
> > Total runtime: 0.087 ms
> > (2 rows)
> >
> > postgres=# EXPLAIN ANALYSE SELECT * FROM parse_url('http://www.postgresql.org/docs/8.4/static/xfunc-c.html#AEN44968', 'path');
> > QUERY PLAN
> > ---------------------------------------------------------------------------------------------------------
> > Function Scan on parse_url (cost=0.00..0.01 rows=1 width=32) (actual time=0.026..0.029 rows=1 loops=1)
> > Total runtime: 0.070 ms
> > (2 rows)
> >
>
>

In response to

Responses

Browse pgsql-fr-generale by date

  From Date Subject
Next Message Rodolphe Quiedeville 2009-10-23 07:21:12 Paquet Debain pgpool2 2.2.5
Previous Message Samuel ROZE 2009-10-22 22:59:43 Re: Gestion des adresses URL avec parse_url