Thread: Commit within a PL/PGSQL procedure

Commit within a PL/PGSQL procedure

From
Harry Broomhall
Date:
   I am trying to develop a special function to read an entire database
and create a new database from it according to various complicated rules.

   Now I could use Perl or similar to do this, but I was under the
impression that doing it on "the backend" in PL/PGSQL was the most efficient.

   The problem I have come up against is that such a function is treated
as a single transaction, so if the database is large the memory gets
eaten up before it finishes.

   I'm told that in the Oracle equivalent system one can insert COMMIT
statements to aleviate the problem.

   Is there any way under PgSQL to do the same?  Or is there some other
'trick' to achieve this?

   Regards,
       Harry.


Re: Commit within a PL/PGSQL procedure

From
Josh Berkus
Date:
Harry,

>    The problem I have come up against is that such a function is treated
> as a single transaction, so if the database is large the memory gets
> eaten up before it finishes.
>
>    I'm told that in the Oracle equivalent system one can insert COMMIT
> statements to aleviate the problem.
>
>    Is there any way under PgSQL to do the same?  Or is there some other
> 'trick' to achieve this?

No.  PostgreSQL's design strategy is that each function is "atomic", or its
own transaction.

Also, is is unlikely that your problem is running out of memory ... far more
likely, later steps in your procedure are suffering from the lack of VACUUM
after earlier steps.   And VACUUM may not be done inside a function.

I suggest that you break up the complicated rules into 5-20 seperate PL/pgSQL
functions, and then call them with a Perl DBI script, with VACUUMs in
between.

I agree, it would be nice to be able to encapsulate this all in the database,
but PL/pgSQL and our procedureal language functionality needs some more work
... (volunteers?)

--
Josh Berkus
Aglio Database Solutions
San Francisco

Re: Commit within a PL/PGSQL procedure

From
Harry Broomhall
Date:
Josh Berkus writes:
> Harry,
>
[ SNIP]

  Many thanks for your reply...

> No.  PostgreSQL's design strategy is that each function is "atomic", or its
> own transaction.
>
> Also, is is unlikely that your problem is running out of memory ... far more
> likely, later steps in your procedure are suffering from the lack of VACUUM
> after earlier steps.   And VACUUM may not be done inside a function.

   The reason I say it runs out of memory is the message:
ERROR:  Memory exhausted in AllocSetAlloc(36)
in the log file, and I am running 'top' and see the process hit 512MB at
about this point!

>
> I suggest that you break up the complicated rules into 5-20 seperate PL/pgSQL
> functions, and then call them with a Perl DBI script, with VACUUMs in
> between.

  In fact my *test* function consists of a simple scan through a database,
and 3 INSERTs into a new table for each record in the original, where
the values inserted are derived from values in the original.

>
> I agree, it would be nice to be able to encapsulate this all in the database,
> but PL/pgSQL and our procedureal language functionality needs some more work
> ... (volunteers?)

   I was begining to realise that I would have to code it up in Perl and
run it from the "front-end".

   And I'm a long way away in expertese to the point that I could
contribute to the functionality!  <grin>

   Regards,
      Harry.


Re: Commit within a PL/PGSQL procedure

From
Josh Berkus
Date:
Harry,

>    The reason I say it runs out of memory is the message:
> ERROR:  Memory exhausted in AllocSetAlloc(36)
> in the log file, and I am running 'top' and see the process hit 512MB at
> about this point!

Hmmm ... this is highly unlikely to be becuase of the transaction.  When
Postgres runs out of available RAM, it starts swapping to disk ... which can
take hours, but will *not* produce that error.

What did you set your shared_buffers and sort_mem to?  What OS are you on?

>   In fact my *test* function consists of a simple scan through a database,
> and 3 INSERTs into a new table for each record in the original, where
> the values inserted are derived from values in the original.

Postgresql should be able to handle this regardless of table size, it's just a
question of speed.

--
Josh Berkus
Aglio Database Solutions
San Francisco

Re: Commit within a PL/PGSQL procedure

From
Tom Lane
Date:
Harry Broomhall <harry.broomhall@uk.easynet.net> writes:
>    The reason I say it runs out of memory is the message:
> ERROR:  Memory exhausted in AllocSetAlloc(36)
> in the log file, and I am running 'top' and see the process hit 512MB at
> about this point!

Sounds like running out of memory to me too ;-)

We have found (and fixed) various intra-function-call memory leaks in
plpgsql in the past, and I wouldn't be surprised to find more.  Which
PG version is this exactly?  If it's current, can you supply a complete
test case to cause the problem?  I'd be happy to look into it.

            regards, tom lane

Re: Commit within a PL/PGSQL procedure

From
Harry Broomhall
Date:
Josh Berkus writes:
> Harry,
>
> >    The reason I say it runs out of memory is the message:
> > ERROR:  Memory exhausted in AllocSetAlloc(36)
> > in the log file, and I am running 'top' and see the process hit 512MB at
> > about this point!
>
> Hmmm ... this is highly unlikely to be becuase of the transaction.  When
> Postgres runs out of available RAM, it starts swapping to disk ... which can
> take hours, but will *not* produce that error.

  At the above mentioned point the swap was about 34% used (normaly it
is about 3%).  It takes about an hour for it to get to this point.

>
> What did you set your shared_buffers and sort_mem to?  What OS are you on?

   FreeBSD 5.0-RELEASE with PostgreSQL 7.3.3

shared_buffers not set - so presumably default of 64
sort_mem not set - so presumably default of 1024

   I haven't fiddled with the conf file on the grounds that I have no real
idea of how to do so - and take the view that I would probably make it worse!

>
> >   In fact my *test* function consists of a simple scan through a database,
> > and 3 INSERTs into a new table for each record in the original, where
> > the values inserted are derived from values in the original.
>
> Postgresql should be able to handle this regardless of table size, it's just a
> question of speed.

   The source file is about 6.4 ^6 records, and the system dies at about
the 1 million mark.

   Regards,
      Harry.


Re: Commit within a PL/PGSQL procedure

From
Tom Lane
Date:
Harry Broomhall <harry.broomhall@uk.easynet.net> writes:
> In fact my *test* function consists of a simple scan through a database,
> and 3 INSERTs into a new table for each record in the original, where
> the values inserted are derived from values in the original.
>    The source file is about 6.4 ^6 records, and the system dies at about
> the 1 million mark.

Now that I think twice, do you have foreign key linkages in the
tables being inserted into?  If so, the most likely explanation is just
that the list of deferred trigger events is getting too large.  This is
a known deficiency on our TODO list (it should be possible to shove the
list out to disk when it gets too large).

            regards, tom lane

Re: Commit within a PL/PGSQL procedure

From
"Mel Jamero"
Date:
>Now I could use Perl or similar to do this, but I was under the
>impression that doing it on "the backend" in PL/PGSQL was the most
efficient.

About 2 years ago, I was under the same impression.  We "took out" a lot of
our stored procedures and functions and converted it -- first into PERL
modules and then later on into C modules.  The improvements were remarkable,
for each of the conversion stages ("db backend" to PERL and then PERL to C).

I have no idea about the memory problem.

HTH.

--
Mel

-----Original Message-----
From: pgsql-novice-owner@postgresql.org
[mailto:pgsql-novice-owner@postgresql.org]On Behalf Of Josh Berkus
Sent: Tuesday, June 17, 2003 11:41 PM
To: Harry Broomhall; pgsql-novice@postgresql.org
Subject: Re: [NOVICE] Commit within a PL/PGSQL procedure


Harry,

>    The problem I have come up against is that such a function is treated
> as a single transaction, so if the database is large the memory gets
> eaten up before it finishes.
>
>    I'm told that in the Oracle equivalent system one can insert COMMIT
> statements to aleviate the problem.
>
>    Is there any way under PgSQL to do the same?  Or is there some other
> 'trick' to achieve this?

No.  PostgreSQL's design strategy is that each function is "atomic", or its
own transaction.

Also, is is unlikely that your problem is running out of memory ... far more
likely, later steps in your procedure are suffering from the lack of VACUUM
after earlier steps.   And VACUUM may not be done inside a function.

I suggest that you break up the complicated rules into 5-20 seperate
PL/pgSQL
functions, and then call them with a Perl DBI script, with VACUUMs in
between.

I agree, it would be nice to be able to encapsulate this all in the
database,
but PL/pgSQL and our procedureal language functionality needs some more work
... (volunteers?)

--
Josh Berkus
Aglio Database Solutions
San Francisco

---------------------------(end of broadcast)---------------------------
TIP 4: Don't 'kill -9' the postmaster


Re: Commit within a PL/PGSQL procedure

From
Harry Broomhall
Date:
Tom Lane writes:
> Harry Broomhall <harry.broomhall@uk.easynet.net> writes:
> > In fact my *test* function consists of a simple scan through a database,
> > and 3 INSERTs into a new table for each record in the original, where
> > the values inserted are derived from values in the original.
> >    The source file is about 6.4 ^6 records, and the system dies at about
> > the 1 million mark.
>
> Now that I think twice, do you have foreign key linkages in the
> tables being inserted into?

   Spot on!   The new table has a field that references an ID in the
original table.

>  If so, the most likely explanation is just
> that the list of deferred trigger events is getting too large.  This is
> a known deficiency on our TODO list (it should be possible to shove the
> list out to disk when it gets too large).

  Any way round this?

  Regards,
      Harry.


Re: Commit within a PL/PGSQL procedure

From
Tom Lane
Date:
Harry Broomhall <harry.broomhall@uk.easynet.net> writes:
> Tom Lane writes:
>> If so, the most likely explanation is just
>> that the list of deferred trigger events is getting too large.  This is
>> a known deficiency on our TODO list (it should be possible to shove the
>> list out to disk when it gets too large).

>   Any way round this?

Not much :-(.  AFAIR there is no way to get the trigger list to be
processed while you're inside your function --- you have to return to
the outer command loop.  (The correctness of this is debatable, but
that's how things work at the moment.)  So you must either break your
work into multiple function calls, or not use foreign keys
while you're building the new table.  You could think about adding
the FK constraint after you're done inserting data.

            regards, tom lane

Documentation Tools

From
"Juliet May"
Date:
Does anyone know of any tools to help in the process of verbally and
graphically documenting a PostgreSql database and it's associated
application. I want/need to be able to show the relationships among tables
and views. I'm currently using DIA which is somewhat similar to Visio but it
is a long drawn out process.

TIA

Julie


Re: Documentation Tools

From
Nabil Sayegh
Date:
Am Mit, 2003-06-18 um 19.57 schrieb Juliet May:
> Does anyone know of any tools to help in the process of verbally and
> graphically documenting a PostgreSql database and it's associated
> application. I want/need to be able to show the relationships among tables
> and views. I'm currently using DIA which is somewhat similar to Visio but it
> is a long drawn out process.

I'm writing such an app at the moment.
It's based on GnomeCanvas for tables to be dragged around.
References are displayed as arrows, columns (actually displayed as rows)
can be teared off and dropped somewhere else, to create references etc.
At the moment I'm too busy but I hope to continue soon.

For the moment you could use pgaccess.

bye
--
 e-Trolley Sayegh & John, Nabil Sayegh
 Tel.: 0700 etrolley /// 0700 38765539
 Fax.: +49 69 8299381-8
 PGP : http://www.e-trolley.de
--
 e-Trolley Sayegh & John, Nabil Sayegh
 Tel.: 0700 etrolley /// 0700 38765539
 Fax.: +49 69 8299381-8
 PGP : http://www.e-trolley.de


Re: Documentation Tools

From
Josh Berkus
Date:
Juliet,

> > Does anyone know of any tools to help in the process of verbally and
> > graphically documenting a PostgreSql database and it's associated
> > application. I want/need to be able to show the relationships among tables
> > and views. I'm currently using DIA which is somewhat similar to Visio but
it
> > is a long drawn out process.

There's some kind of a db documentation tool on GBORG:
gborg.postgresql.org

--
-Josh Berkus
 Aglio Database Solutions
 San Francisco


Re: Documentation Tools

From
Jorge Ramirez
Date:
Hello, are you using the UML diagrams????, you could use the
postgresautodoc.pl
look for it in freshmeat...

it generates an UML diagram, a docbook doc and mmmm, i don't remember if
a html file...

Regards,
Jorge Ramirez.
http://www.chicolinux.com.mx/



El mié, 18 de 06 de 2003 a las 12:57, Juliet May escribió:
> Does anyone know of any tools to help in the process of verbally and
> graphically documenting a PostgreSql database and it's associated
> application. I want/need to be able to show the relationships among tables
> and views. I'm currently using DIA which is somewhat similar to Visio but it
> is a long drawn out process.
>
> TIA
>
> Julie
>
>
> ---------------------------(end of broadcast)---------------------------
> TIP 6: Have you searched our list archives?
>
>                http://archives.postgresql.org


Re: Documentation Tools

From
"Juliet May"
Date:
Thanks for the suggestion. I don't have time to experiment with it today,
but it definately looks helpful. Right about now I am wishing I had asked my
question before I used DIA to diagram out the majority of my database. And
yes, I did use the UML diagram tool, although I'm guessing I probably didn't
use it correctly.

Thanks to everyone else for their suggestions too.
<snip>
----- Original Message -----
From: "Jorge Ramirez" <jramirez@gvicda.com.mx>


> Hello, are you using the UML diagrams????, you could use the
> postgresautodoc.pl
> look for it in freshmeat...
>
> it generates an UML diagram, a docbook doc and mmmm, i don't remember if
> a html file...

</snip>


Re: Documentation Tools

From
Douglas Trainor
Date:
http://freshmeat.net/projects/postgresql_autodoc/?topic_id=66

Jorge Ramirez wrote:

>Hello, are you using the UML diagrams????, you could use the
>postgresautodoc.pl
>look for it in freshmeat...
>
>it generates an UML diagram, a docbook doc and mmmm, i don't remember if
>a html file...
>
>Regards,
>Jorge Ramirez.
>http://www.chicolinux.com.mx/
>
>
>
>El mié, 18 de 06 de 2003 a las 12:57, Juliet May escribió:
>
>
>>Does anyone know of any tools to help in the process of verbally and
>>graphically documenting a PostgreSql database and it's associated
>>application. I want/need to be able to show the relationships among tables
>>and views. I'm currently using DIA which is somewhat similar to Visio but it
>>is a long drawn out process.
>>
>>TIA
>>
>>Julie
>>
>>




Re: Documentation Tools

From
Nabil Sayegh
Date:
Am Mit, 2003-06-18 um 19.57 schrieb Juliet May:
> Does anyone know of any tools to help in the process of verbally and
> graphically documenting a PostgreSql database and it's associated
> application. I want/need to be able to show the relationships among tables
> and views. I'm currently using DIA which is somewhat similar to Visio but it
> is a long drawn out process.

I'm writing such an app at the moment.
It's based on GnomeCanvas for tables to be dragged around.
References are displayed as arrows, columns (actually displayed as rows)
can be teared off and dropped somewhere else, to create references etc.
At the moment I'm too busy but I hope to continue soon.

For the moment you could use pgaccess.

bye
--
 e-Trolley Sayegh & John, Nabil Sayegh
 Tel.: 0700 etrolley /// 0700 38765539
 Fax.: +49 69 8299381-8
 PGP : http://www.e-trolley.de


Re: Commit within a PL/PGSQL procedure

From
Harry Broomhall
Date:
Tom Lane writes:
> Harry Broomhall <harry.broomhall@uk.easynet.net> writes:
> > Tom Lane writes:
> >> If so, the most likely explanation is just
> >> that the list of deferred trigger events is getting too large.  This is
> >> a known deficiency on our TODO list (it should be possible to shove the
> >> list out to disk when it gets too large).
>
> >   Any way round this?
>
> Not much :-(.  AFAIR there is no way to get the trigger list to be
> processed while you're inside your function --- you have to return to
> the outer command loop.  (The correctness of this is debatable, but
> that's how things work at the moment.)  So you must either break your
> work into multiple function calls, or not use foreign keys
> while you're building the new table.  You could think about adding
> the FK constraint after you're done inserting data.


  FYI:

  I removed the foreign key from the table definition and tried again
from scratch.

  The function went through with no problems, and 'top' showed that the
backend barely broke sweat, keeping a low memory useage throughout.

  So I've now started to rewrite the thing with this experience in mind.

  Many thanks for your insight and help.

  Regards,
     Harry.