X-Original-To: pgsql-performance-postgresql.org@postgresql.org Received: from localhost (mx1.hub.org [200.46.208.251]) by postgresql.org (Postfix) with ESMTP id B79019FA5BA for ; Thu, 15 Jun 2006 11:24:13 -0300 (ADT) Received: from postgresql.org ([200.46.204.71]) by localhost (mx1.hub.org [200.46.208.251]) (amavisd-new, port 10024) with ESMTP id 01178-08 for ; Thu, 15 Jun 2006 11:24:08 -0300 (ADT) X-Greylist: from auto-whitelisted by SQLgrey- Received: from sss.pgh.pa.us (sss.pgh.pa.us [66.207.139.130]) by postgresql.org (Postfix) with ESMTP id 5436C9F9CAA for ; Thu, 15 Jun 2006 11:24:08 -0300 (ADT) Received: from sss2.sss.pgh.pa.us (tgl@localhost [127.0.0.1]) by sss.pgh.pa.us (8.13.6/8.13.6) with ESMTP id k5FEO4UF027706; Thu, 15 Jun 2006 10:24:04 -0400 (EDT) To: "Mindaugas" cc: pgsql-performance@postgresql.org Subject: Re: How to analyze function performance In-reply-to: <016401c69075$8a35e8c0$f20214ac@bite.lt> References: <016401c69075$8a35e8c0$f20214ac@bite.lt> Comments: In-reply-to "Mindaugas" message dated "Thu, 15 Jun 2006 15:16:32 +0300" Date: Thu, 15 Jun 2006 10:24:04 -0400 Message-ID: <27705.1150381444@sss.pgh.pa.us> From: Tom Lane X-Virus-Scanned: Maia Mailguard 1.0.1 X-Archive-Number: 200606/302 X-Sequence-Number: 19659 "Mindaugas" writes: > Is it possible to somehow analyze function performance? E.g. > we are using function cleanup() which takes obviously too much time > to execute but I have problems trying to figure what is slowing things > down. > When I explain analyze function lines step by step it show quite > acceptable performance. Are you sure you are "explain analyze"ing the same queries the function is really doing? You have to account for the fact that what plpgsql is issuing is parameterized queries, and sometimes that limits the planner's ability to pick a good plan. For instance, if you have declare x int; begin ... for r in select * from foo where key = x loop ... then what is really getting planned and executed is "select * from foo where key = $1" --- every plpgsql variable gets replaced by a parameter symbol "$n". You can model this for EXPLAIN purposes with a prepared statement: prepare p1(int) as select * from foo where key = $1; explain analyze execute p1(42); If you find out that a particular query really sucks when parameterized, you can work around this by using EXECUTE to force the query to be planned afresh on each use with literal constants instead of parameters: for r in execute 'select * from foo where key = ' || x loop ... The replanning takes extra time, though, so don't do this except where you've specifically proved there's a need. BTW, be careful to use quote_literal() when needed in queries built as strings, else you'll have bugs and maybe even security problems. regards, tom lane