Re: [HACKERS] getting composite types info from libpq

From: Florian Pflug <fgp(at)phlo(dot)org>
To: Daniele Varrazzo <daniele(dot)varrazzo(at)gmail(dot)com>
Cc: Merlin Moncure <mmoncure(at)gmail(dot)com>, PostgreSQL Hackers <pgsql-hackers(at)postgresql(dot)org>, pgsql-general(at)postgresql(dot)org
Subject: Re: [HACKERS] getting composite types info from libpq
Date: 2010-12-16 10:03:36
Message-ID: 16CCB2D3-197E-4D9F-BC6F-9B123EA0D40D@phlo.org
Views: Raw Message | Whole Thread | Download mbox | Resend email
Thread:
Lists: pgsql-general pgsql-hackers

On Dec16, 2010, at 02:51 , Daniele Varrazzo wrote:
> 1. do I get enough info in the PGresult to inspect anonymous composite types?
You just get the composite value, as you discovered. In text mode, that means
only the composite string value, which contains no information about the
individual field's types. In binary mode, however, the structure of such a
composite value appears to be

<number of fields: 4 bytes>
[for each field]
<OID of field's type: sizeof(Oid) bytes>
[if value is NULL]
<-1: 4 bytes>
[else]
<length of value: 4 bytes>
<value: <length> bytes>
[end if]
[end for]

according to a quick glance over record_send() in
src/backend/utils/rowtypes.c. You'll want to double-check this, it really
was a *very* quick glance ;-)

The field's values are, again, in binary format, not text! AFAIK you *can*
decide whether to use text for binary mode on a per-field basis when you
execute a query, but once you request a field of type "record" to be
transferred as binary, you'll have to be able to deal with arbitrary types
sent as binary since you won't know which types the record might contain.
Which isn't easy, because the binary representation of some types
(like float I think) is machine-dependent :-(

> 2. do I get such info for composite types for which I have schema info
> in the catalog, without issuing a second query? (which I don't feel it
> is a driver's job)
No. Your only option is probably to query this information once and cache
it. Knowing when to invalidate that cache isn't easy, though - but since
type's probably don't change too often, some compromise will hopefully do.

> 3. is there any libpq facility to split the string returned after a
> composite types into its single components, without having to write a
> parser to deal with commas and quotes?
Not that I'd know of. There is, however, a project called libpqtypes
which I think deal with things like that. I've never used it, though,
so I can't say whether it fits your needs or not.

> 4. are by any chance those info passed on the network, maybe available
> in an internal libpq structure, but then not accessible from the libpq
> interface?
Don't think so.

FYI, There has been some discussion about providing SQL-accessible functions
to inspect and modify field of arbitrary records. There are two
implementations of such a thing that I know of

One was written by me, and is available at
https://github.com/fgp/pg_record_inspect

The other was written by Pavel Stehule and is described in his blob here
http://okbob.blogspot.com/2010/12/iteration-over-record-in-plpgsql.html

Neither of these helps much with doing things on the driver level, though,
unless you're willing to tell your users to select
record_inspect.fieldinfo(some_record) as "some_record.fieldinfo"
alongside "some_record" if they want the record to be represented as other
than one large string.

best regards,
Florian Pflug

In response to

Responses

Browse pgsql-general by date

  From Date Subject
Next Message Robert Gravsjö 2010-12-16 10:07:58 Re: How to restore from backup to 8.4.3 server using 9.0 dump/restore
Previous Message Anupama Ramaswamy 2010-12-16 09:54:29 plperl - caching prepared queries and cleanup

Browse pgsql-hackers by date

  From Date Subject
Next Message Greg Smith 2010-12-16 10:12:52 Re: directory archive format for pg_dump
Previous Message Shigeru HANADA 2010-12-16 09:45:52 Re: SQL/MED - file_fdw