<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>IAmA DBA AMA</title>
	<atom:link href="http://blog.kimiensoftware.com/feed" rel="self" type="application/rss+xml" />
	<link>http://blog.kimiensoftware.com</link>
	<description>PostgreSQL Blog for Oracle DBAs</description>
	<lastBuildDate>Fri, 16 Mar 2012 09:42:36 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.2.1</generator>
		<item>
		<title>Back to Oracle</title>
		<link>http://blog.kimiensoftware.com/2012/03/back-to-oracle-395</link>
		<comments>http://blog.kimiensoftware.com/2012/03/back-to-oracle-395#comments</comments>
		<pubDate>Fri, 16 Mar 2012 09:42:36 +0000</pubDate>
		<dc:creator>Nathan Thom</dc:creator>
				<category><![CDATA[Oracle]]></category>

		<guid isPermaLink="false">http://blog.kimiensoftware.com/?p=395</guid>
		<description><![CDATA[I haven&#8217;t posted in a while. In fact, I&#8217;m back with working on Oracle databases. Working with PostgreSQL was a great experience, and certainly taught me plenty of things. I [...]]]></description>
			<content:encoded><![CDATA[<p>I haven&#8217;t posted in a while. In fact, I&#8217;m back with working on Oracle databases. Working with PostgreSQL was a great experience, and certainly taught me plenty of things. I have migrated the databases for all my personal projects onto PostgreSQL (except WordPress&#8230;. grrrr when will they get off mysql) without hesitation.</p>
<p>Anyway, I may or may not write about Oracle here &#8211; there&#8217;s so much else out there already I don&#8217;t feel like I can contribute much else.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.kimiensoftware.com/2012/03/back-to-oracle-395/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Upgrading PostGIS</title>
		<link>http://blog.kimiensoftware.com/2011/09/upgrading-postgis-391</link>
		<comments>http://blog.kimiensoftware.com/2011/09/upgrading-postgis-391#comments</comments>
		<pubDate>Fri, 02 Sep 2011 00:16:50 +0000</pubDate>
		<dc:creator>Nathan Thom</dc:creator>
				<category><![CDATA[Linux]]></category>
		<category><![CDATA[PostgreSQL]]></category>
		<category><![CDATA[Install]]></category>
		<category><![CDATA[postgis]]></category>
		<category><![CDATA[Upgrade]]></category>

		<guid isPermaLink="false">http://blog.kimiensoftware.com/?p=391</guid>
		<description><![CDATA[I am upgrading a PostgreSQL test server from 8.3 to 9.0, as well as PostGIS from 1.3 to 1.5. At one stage I kept getting the following error while trying [...]]]></description>
			<content:encoded><![CDATA[<p>I am upgrading a PostgreSQL test server from 8.3 to 9.0, as well as PostGIS from 1.3 to 1.5. At one stage I kept getting the following error while trying to install the PostGIS database.</p>
<pre class="brush: plain; title: ; notranslate">
$ psql mydb -f postgis.sql
SET
BEGIN
psql:postgis.sql:59: ERROR:  could not load library "/usr/pgsql-9.0/lib/postgis-1.5.so": /usr/pgsql-9.0/lib/postgis-1.5.so: undefined symbol: GEOSHausdorffDistance
psql:postgis.sql:65: ERROR:  current transaction is aborted, commands ignored until end of transaction block
psql:postgis.sql:70: ERROR:  current transaction is aborted, commands ignored until end of transaction block
-snip-
</pre>
<p>After a lot of head banging (the brick wall kind, not the heavy metal kind), I figured out I still had the old version of the GEOS library:</p>
<pre class="brush: plain; title: ; notranslate">
# yum list geos
Loaded plugins: rhnplugin, security
Excluding Packages from rhel5s-x86_64 - Base (RPData)
Finished
Excluding Packages from rhel5s-x86_64 - Updates (RPData)
Finished
Installed Packages
geos.x86_64                                                                                                    2.2.3-2.rhel5                                                                                                     installed
Available Packages
geos.x86_64                                                                                                    3.2.2-1.rhel5                                                                                                     postgresql9
</pre>
<p>A quick upgrade of GEOS to v3 and all was well.</p>
<pre class="brush: plain; title: ; notranslate">
$ psql mydb -f postgis.sql
SET
BEGIN
CREATE FUNCTION
CREATE FUNCTION
-snip-
</pre>
]]></content:encoded>
			<wfw:commentRss>http://blog.kimiensoftware.com/2011/09/upgrading-postgis-391/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Installation Frustrations</title>
		<link>http://blog.kimiensoftware.com/2011/08/installation-frustrations-386</link>
		<comments>http://blog.kimiensoftware.com/2011/08/installation-frustrations-386#comments</comments>
		<pubDate>Tue, 30 Aug 2011 23:04:43 +0000</pubDate>
		<dc:creator>Nathan Thom</dc:creator>
				<category><![CDATA[Linux]]></category>
		<category><![CDATA[Install]]></category>
		<category><![CDATA[PostgreSQL]]></category>
		<category><![CDATA[Upgrade]]></category>
		<category><![CDATA[Versions]]></category>

		<guid isPermaLink="false">http://blog.kimiensoftware.com/?p=386</guid>
		<description><![CDATA[I am bad at linux installations. Really really bad. This post is more of a rant than anything useful I messed up the auto start service while testing out some [...]]]></description>
			<content:encoded><![CDATA[<p>I am bad at linux installations. Really really bad. This post is more of a rant than anything useful <img src='http://blog.kimiensoftware.com/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
<p>I messed up the auto start service while testing out some upgrades and needed to reinstall the postgresql 8.3 server package:</p>
<pre class="brush: bash; title: ; notranslate">
# rpm -i postgresql-server-8.3.13-1PGDG.x86_64.rpm
package postgresql-server-8.3.13-1PGDG.x86_64 is already installed
</pre>
<p>Umm OK I’ll remove it first then:</p>
<pre class="brush: bash; title: ; notranslate">
# rpm -e postgresql-server-8.3.13-1PGDG.x86_64.rpm
error: package postgresql-server-8.3.13-1PGDG.x86_64.rpm is not installed
</pre>
<p>Umm OK. What does yum have to say:</p>
<pre class="brush: bash; title: ; notranslate">
# yum list installed postgresql\*
Loaded plugins: rhnplugin, security

Installed Packages
postgresql.x86_64 8.3.13-1PGDG installed
postgresql-contrib.x86_64 8.3.13-1PGDG installed
postgresql-libs.x86_64 8.3.13-1PGDG installed
postgresql-plperl.x86_64 8.3.13-1PGDG installed
postgresql-plpython.x86_64 8.3.13-1PGDG installed
postgresql-pltcl.x86_64 8.3.13-1PGDG installed
postgresql-server.x86_64 8.3.13-1PGDG installed
</pre>
<p>So yum thinks it&#8217;s installed. Let’s try removing it with yum:</p>
<pre class="brush: bash; title: ; notranslate">
# yum remove postgresql-server
Loaded plugins: rhnplugin, security

============================================================================================================================================================================================================================================
Package Arch Version Repository Size
============================================================================================================================================================================================================================================
Removing:
postgresql-server x86_64 8.3.13-1PGDG installed 12 M
Removing for dependencies:
postgresql-plperl x86_64 8.3.13-1PGDG installed 72 k
postgresql-plpython x86_64 8.3.13-1PGDG installed 49 k
postgresql-pltcl x86_64 8.3.13-1PGDG installed 50 k

Transaction Summary
============================================================================================================================================================================================================================================
Install 0 Package(s)
Update 0 Package(s)
Remove 4 Package(s)

Is this ok [y/N]: y
Downloading Packages:
Running rpm_check_debug
Running Transaction Test
Finished Transaction Test
Transaction Test Succeeded
Running Transaction
error reading information on service postgresql: No such file or directory
Erasing : postgresql-pltcl 1/4
error: %preun(postgresql-server-8.3.13-1PGDG.x86_64) scriptlet failed, exit status 1
Erasing : postgresql-plpython 2/4
Erasing : postgresql-plperl 3/4

Removed:
postgresql-server.x86_64 0:8.3.13-1PGDG

Dependency Removed:
postgresql-plperl.x86_64 0:8.3.13-1PGDG postgresql-plpython.x86_64 0:8.3.13-1PGDG postgresql-pltcl.x86_64 0:8.3.13-1PGDG

Complete!
</pre>
<p>Well it removed the dependency language packages, but not the server package. Fair enough, the postgresql service is indeed missing but why should that stop the uninstall?</p>
<pre class="brush: bash; title: ; notranslate">
# chkconfig --list postgresql
error reading information on service postgresql: No such file or directory
</pre>
<p>I added the service back manually by recreating the /etc/init.d/postgresql file (copied a different server) and then made sure it could add and recognise the service:</p>
<pre class="brush: bash; title: ; notranslate">
# chkconfig --add postgresql
# chkconfig --list postgresql
postgresql 0:off 1:off 2:off 3:off 4:off 5:off 6:off
</pre>
<p>Now a yum remove works:</p>
<pre class="brush: bash; title: ; notranslate">
# yum remove postgresql-server
Loaded plugins: rhnplugin, security

============================================================================================================================================================================================================================================
Package Arch Version Repository Size
============================================================================================================================================================================================================================================
Removing:
postgresql-server x86_64 8.3.13-1PGDG installed 12 M

Transaction Summary
============================================================================================================================================================================================================================================
Install 0 Package(s)
Update 0 Package(s)
Remove 1 Package(s)

Is this ok [y/N]: y
Downloading Packages:
Running rpm_check_debug
Running Transaction Test
Finished Transaction Test
Transaction Test Succeeded
Running Transaction
Erasing : postgresql-server 1/1
warning: /var/lib/pgsql/.bash_profile saved as /var/lib/pgsql/.bash_profile.rpmsave

Removed:
postgresql-server.x86_64 0:8.3.13-1PGDG

Complete!
</pre>
<p>Yay, now I know what to do the next time I mess it up&#8230; in about 5 mins.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.kimiensoftware.com/2011/08/installation-frustrations-386/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Session hanging with no locking pid</title>
		<link>http://blog.kimiensoftware.com/2011/08/session-hanging-with-no-locking-pid-380</link>
		<comments>http://blog.kimiensoftware.com/2011/08/session-hanging-with-no-locking-pid-380#comments</comments>
		<pubDate>Mon, 01 Aug 2011 08:10:03 +0000</pubDate>
		<dc:creator>Nathan Thom</dc:creator>
				<category><![CDATA[Linux]]></category>
		<category><![CDATA[PostgreSQL]]></category>
		<category><![CDATA[Locking]]></category>
		<category><![CDATA[psql]]></category>
		<category><![CDATA[Transactions]]></category>

		<guid isPermaLink="false">http://blog.kimiensoftware.com/?p=380</guid>
		<description><![CDATA[I was trying to drop a schema, but it was hanging. My whats running script didn&#8217;t help too much: So something is blocking the drop, but there are no details [...]]]></description>
			<content:encoded><![CDATA[<p>I was trying to drop a schema, but it was hanging. My <a href="http://kimiensoftware.com/software/downloads">whats running script</a> didn&#8217;t help too much:</p>
<pre class="brush: bash; title: ; notranslate">
$ db_running.sh
   datname   | procpid | usename  |           sql            |       age       | query_ip | locktype |      mode       | hold_sql | blocker_pid | blocker_ip
-------------+---------+----------+--------------------------+-----------------+----------+----------+-----------------+----------+-------------+------------
 mydb        |   10371 | postgres | drop schema old cascade; | 00:05:17.994846 |          | relation | AccessShareLock |          |             |
</pre>
<p>So something is blocking the drop, but there are no details as to what who it is. Looking at the pg_locks rows of interest:</p>
<pre class="brush: sql; title: ; notranslate">
mydb=# select * from pg_locks where relation=437506;
 locktype | database | relation | page | tuple | virtualxid | transactionid | classid | objid | objsubid | virtualtransaction |  pid  |        mode         | granted
----------+----------+----------+------+-------+------------+---------------+---------+-------+----------+--------------------+-------+---------------------+---------
 relation |    16384 |   437506 |      |       |            |               |         |       |          | 2/5                | 10371 | AccessExclusiveLock | f
 relation |    16384 |   437506 |      |       |            |               |         |       |          | -1/30795916        |       | AccessShareLock     | t
(2 rows)
</pre>
<p>Whatever is blocking my session has no PID or transaction. From past experience, I know that weird locking behavior like this is usually due to prepared transactions (gaah I hate them!). Sure enough:</p>
<pre class="brush: sql; title: ; notranslate">
postgres=# select * from pg_prepared_xacts ;
 transaction |                                                                    gid                                                                    |           prepared            |  owner   |  database
-------------+-------------------------------------------------------------------------------------------------------------------------------------------+-------------------------------+----------+-------------
    30795916 | 4871251_a5kEAHHYB2tlcHBsaW4wMS1nZmgscnBwLXNpdGVhLW5vZGUwMS1pbnN0MDEsUDMzNzAw_ZXBwbGluMDEtZ2ZoLHJwcC1zaXRlYS1ub2RlMDEtaW5zdDAxLFAzMzcwMCwB | 2011-07-27 23:56:24.371114+10 | postgres | mydb
(1 row)
</pre>
<p>It&#8217;s a few days old and the owning process is dead. Let&#8217;s remove it:</p>
<pre class="brush: sql; title: ; notranslate">
postgres=# \c mydb
You are now connected to database "mydb".
mydb=# rollback prepared '4871251_a5kEAHHYB2tlcHBsaW4wMS1nZmgscnBwLXNpdGVhLW5vZGUwMS1pbnN0MDEsUDMzNzAw_ZXBwbGluMDEtZ2ZoLHJwcC1zaXRlYS1ub2RlMDEtaW5zdDAxLFAzMzcwMCwB';
ROLLBACK PREPARED
</pre>
<p>And my blocked session immediate resumed and completed the drop.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.kimiensoftware.com/2011/08/session-hanging-with-no-locking-pid-380/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Windows PostgreSQL and the case of the vanishing libint.dll</title>
		<link>http://blog.kimiensoftware.com/2011/07/windows-postgresql-and-the-case-of-the-vanishing-libint-dll-372</link>
		<comments>http://blog.kimiensoftware.com/2011/07/windows-postgresql-and-the-case-of-the-vanishing-libint-dll-372#comments</comments>
		<pubDate>Tue, 12 Jul 2011 02:11:01 +0000</pubDate>
		<dc:creator>Nathan Thom</dc:creator>
				<category><![CDATA[PostgreSQL]]></category>
		<category><![CDATA[Windows]]></category>
		<category><![CDATA[Install]]></category>
		<category><![CDATA[Security]]></category>

		<guid isPermaLink="false">http://blog.kimiensoftware.com/?p=372</guid>
		<description><![CDATA[My PostgreSQL 9.0.3 databases running on Windows Server 2008 R2 64-bit were refusing to start. The server was rebooted unexpectedly with no clean shutdown and when it came back up, [...]]]></description>
			<content:encoded><![CDATA[<p>My PostgreSQL 9.0.3 databases running on Windows Server 2008 R2 64-bit were refusing to start. The server was rebooted unexpectedly with no clean shutdown and when it came back up, PostgreSQL didn’t. I always have such fun with Windows servers, so here we go&#8230;</p>
<p>1.	Open the Services control panel and try to start the postgresql-x64-9.0 service:</p>
<pre class="brush: plain; title: ; notranslate">
Windows could not start the postgresql-x64-9.0 – PostgreSQL Server 9.0 service on Local Computer.

Error 1053: The service did not respond to the start or control request in a timely fashion.
</pre>
<p>This error pops up immediately; there is no real timeout in play here. There was nothing in the PostgreSQL log file, so it must be something to do with Windows. Some Googling tells me to make sure the user starting the service is not an administrator. It uses the postgres user, and I don’t know how to check if it has administrator privileges as Windows seems to deny its existence when I open the users from the control panel.</p>
<p>The Security Events show a successful logon audit for the postgres user so there’s no password issues.</p>
<p>2.	Try to start it manually from a DOS prompt:</p>
<pre class="brush: plain; title: ; notranslate">
C:\Users\ntm\pg_ctl start
The program can't start because libintl.dll is missing from your computer. 

Try reinstalling the program to fix this problem.
</pre>
<p>I see libintl-8.dll under C:\Program Files (x86)\psqlODBC\0900\bin, but nothing under C:\Program Files\psqlODBC\0900\bin or C:\Program Files\PostgreSQL\9.0\bin, and no libintl.dll file anywhere.</p>
<p>3.	I added the Program Files (x86) directory to the path environment variable, copied the file to libintl.dll, and this time got:</p>
<pre class="brush: plain; title: ; notranslate">
The application was unable to start correctly (0xc000007b).
</pre>
<p>OK, so I assume that file was a 32-bit library, where as I need a 64-bit one.</p>
<p>4.	I reinstalled PostgreSQL 9.0.3 64-bit. This failed with the message:</p>
<pre class="brush: plain; title: ; notranslate">
Problem running post-install step. Installation may not complete correctly.
Failed to start the database server.
</pre>
<p>When I checked, it did put libintl.dll in C:\Program Files\PostgreSQL\9.0\bin which is progress I guess. </p>
<p>5.	Let’s try to start the service via Control Panel:</p>
<pre class="brush: plain; title: ; notranslate">
The specified service has been marked for deletion.
</pre>
<p>I closed and re-opened the services page, and then it had disappeared completely.</p>
<p>6.	OK, let’s try starting it manually again:</p>
<pre class="brush: plain; title: ; notranslate">
C:\Users\ntm>runas /user:postgres "pg_ctl start"
Enter the password for postgres:
Attempting to start pg_ctl start as user "BPPWIN01-CL-SQL\postgres" ...
</pre>
<p>Some screen popped up briefly, disappeared, didn’t work and didn’t tell me what was wrong. Awesome.</p>
<p>7.	Reinstalled. Again. This time the installer ran to success (yay) but wants to restart (grrr). I’ll take that under advisement and keep going.</p>
<p>8.	The service is back, so tried to start it.</p>
<pre class="brush: plain; title: ; notranslate">
Windows could not start the postgresql-x64-9.0 – PostgreSQL Server 9.0 service on Local Computer.

Error 1053: The service did not respond to the start or control request in a timely fashion.
</pre>
<p>This time it did take forever before erroring. I checked the security on all the PostgreSQL folders and found that the data directory did not have read/write access for the postgres user.</p>
<p>9.	Give postgres user access to its own data, and tried to start the service.</p>
<p>Success! I can now logon. So two questions remain:</p>
<p>1.	Why did it lose its dll file/security/whatever else I didn’t see? Was it the unclean shutdown, or some recent patch, or something else just waiting for a reboot to screw me over?<br />
2.	Why does Windows hate me so much?</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.kimiensoftware.com/2011/07/windows-postgresql-and-the-case-of-the-vanishing-libint-dll-372/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Queries Running for Negative Time</title>
		<link>http://blog.kimiensoftware.com/2011/07/queries-running-for-negative-time-369</link>
		<comments>http://blog.kimiensoftware.com/2011/07/queries-running-for-negative-time-369#comments</comments>
		<pubDate>Thu, 07 Jul 2011 22:40:46 +0000</pubDate>
		<dc:creator>Nathan Thom</dc:creator>
				<category><![CDATA[Linux]]></category>
		<category><![CDATA[PostgreSQL]]></category>
		<category><![CDATA[psql]]></category>
		<category><![CDATA[Scripts]]></category>
		<category><![CDATA[Transactions]]></category>

		<guid isPermaLink="false">http://blog.kimiensoftware.com/?p=369</guid>
		<description><![CDATA[I have a script db_running.sh that shows me what queries are currently running on a server and what queries are blocking them, if any. One thing I’ve finally gotten around [...]]]></description>
			<content:encoded><![CDATA[<p>I have a script db_running.sh that shows me what queries are currently running on a server and what queries are blocking them, if any. One thing I’ve finally gotten around to questioning is why my script sometimes gives a negative age for the queries, eg:</p>
<pre class="brush: plain; title: ; notranslate">
$ db_running.sh
 datname | procpid | usename  |                                                 sql                                                  |       age        |  query_ip   | L? | locktype | hold_sql | blocker_ip
---------+---------+----------+------------------------------------------------------------------------------------------------------+------------------+-------------+----+----------+----------+------------
 ntm     |   20163 | postgres | &lt;IDLE> in transaction                                                                                | 00:00:00.455019  | 172.17.0.51 | f  |          |          |
 ntm     |   20535 | postgres | &lt;IDLE> in transaction                                                                                | 00:00:00.004358  | 172.17.0.23 | f  |          |          |
 ntm     |   19974 | postgres | COMMIT                                                                                               | -00:00:00.001497 | 172.17.0.53 | f  |          |          |
 ntm     |   20116 | postgres | select contacts0_.customer_poid as customer9_1_, contacts0_.contact_poid as contact1_1_, contacts0_. | -00:00:00.0051   | 172.17.0.21 | f  |          |          |
(4 rows)
</pre>
<p>I am calculating the age via:</p>
<p>select &#8230; , current_timestamp-s.query_start as age, &#8230;</p>
<p>The current_timestamp function I’m using will get the time at the start of the current transaction (i.e. my select statement) so that it does not change for each row being returned (<a href="http://www.postgresql.org/docs/9.0/static/functions-datetime.html#FUNCTIONS-DATETIME-CURRENT">doco reference</a>). This is pretty much always want you want.</p>
<p>However when querying the pg_stat_activity view, it does not actually return the session details as at the start of your transaction but rather it returns the session details as at the time you first query it inside your transaction. Or in the words of the <a href="http://www.postgresql.org/docs/9.0/static/monitoring-stats.html">documentation</a>:</p>
<p><em>&#8220;information about the current queries of all sessions is collected when any such information is first requested within a transaction&#8221;</em></p>
<p>What I guess is happening is that my select query starts, gets the current_timestamp value, then a few milliseconds later calls the pg_stat_activity view which can potentially see sessions that started just after my original select started. Hence current_timestamp &#8211; query_start becomes negative!</p>
<p>A quick scan of the available date/time functions revealed clock_timestamp() which always returns the timestamp at the time the function is called and is not transaction aware. This sounds like a good alternative for my script, and testing it out confirms my theory:</p>
<pre class="brush: plain; title: ; notranslate">
$ db_running.sh
 datname | procpid | usename  |                                                 sql                                                  |       age        |      age2       | client_addr | L? | locktype | hold_sql | client_addr
---------+---------+----------+------------------------------------------------------------------------------------------------------+------------------+-----------------+-------------+----+----------+----------+-------------
 ntm     |   14874 | postgres | &lt;IDLE> in transaction                                                                                | 00:00:09.15277   | 00:00:09.161446 | 172.17.0.52 | f  |          |          |
 ntm     |   14770 | postgres | COMMIT PREPARED '4871251_B/sBAG7s7uFhcHBsaW4wMy1nbGFzcyxycHAtc2l0ZWItbm9kZTAzLWluc3QwMixQMzM3MDE=_YX | 00:00:00.027994  | 00:00:00.036554 | 172.17.0.53 | f  |          |          |
 ntm     |   14873 | postgres | COMMIT                                                                                               | 00:00:00.009249  | 00:00:00.017878 | 172.17.0.52 | f  |          |          |
 ntm     |   13361 | postgres | &lt;IDLE> in transaction                                                                                | -00:00:00.004689 | 00:00:00.004038 | 172.17.0.21 | f  |          |          |
(4 rows)
</pre>
<p>I’ve yet to see a negative value re-appear after using this new function. My OCD can breathe a little easier now <img src='http://blog.kimiensoftware.com/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' /> </p>
<p>You can download my <a href="http://kimiensoftware.com/software/downloads">db_running.sh script here</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.kimiensoftware.com/2011/07/queries-running-for-negative-time-369/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Debugging ShareLock on Transaction</title>
		<link>http://blog.kimiensoftware.com/2011/07/debugging-sharelock-on-transaction-363</link>
		<comments>http://blog.kimiensoftware.com/2011/07/debugging-sharelock-on-transaction-363#comments</comments>
		<pubDate>Fri, 01 Jul 2011 05:55:43 +0000</pubDate>
		<dc:creator>Nathan Thom</dc:creator>
				<category><![CDATA[PostgreSQL]]></category>
		<category><![CDATA[Locking]]></category>
		<category><![CDATA[Logs]]></category>
		<category><![CDATA[Transactions]]></category>
		<category><![CDATA[Vacuum]]></category>

		<guid isPermaLink="false">http://blog.kimiensoftware.com/?p=363</guid>
		<description><![CDATA[An issue I’ve been trying to understand recently is a bunch of ShareLock warnings in the log file. And a bit later The problem went away before I could run [...]]]></description>
			<content:encoded><![CDATA[<p>An issue I’ve been trying to understand recently is a bunch of ShareLock warnings in the log file.</p>
<pre class="brush: plain; title: ; notranslate">
LOG:  process 916 still waiting for ShareLock on transaction 378662803 after 1000.762 ms
STATEMENT:  update user_customers set last_changed=$1 where id=$20
</pre>
<p>And a bit later</p>
<pre class="brush: plain; title: ; notranslate">
LOG:  process 916 acquired ShareLock on transaction 378662803 after 1777.653 ms
STATEMENT:  update user_customers set last_changed=$1 where id=$20
LOG:  duration: 2030.106 ms  execute : update user_customers set last_changed=$1 where id=$20
</pre>
<p>The problem went away before I could run a query to find out what process was holding the lock, and I’ve never been able to catch it in the act. What can we tell from this logged information?</p>
<p>1.	The type of lock that it was trying to grab was a Share lock.<br />
2.	The statement that is trying to grab a lock is an UPDATE.<br />
3.	The object being locked is a Transaction (not tuple).<br />
4.	There was only the one duration line, so whatever is holding the lock was quick (<1 sec).</p>
<p>A Share lock would mean the locking process is holding one of the following on the transaction:<br />
•	Row exclusive (update, delete, insert)<br />
•	Share update exclusive (vacuum, analyze)<br />
•	Share row exclusive (not used automatically by postgres processes)<br />
•	Exclusive (not used automatically by postgres processes)<br />
•	Access exclusive (alter, drop, truncate, reindex, cluster, vacuum full)</p>
<p>I know this particular database has no DDL running and the code does not perform any explicit locking so I can rule out the last 3, leaving Row Exclusive and Share Update Exclusive. I ruled out any autovacuum processing from blocking the updates in my <a href="http://blog.kimiensoftware.com/2011/06/vacuum-locks-358">previous post</a>.</p>
<p>So that just leaves Row Exclusive as the possible cause of this blocking. However, remember that my lock is waiting on a transaction not a row. This indicates that some session has a Row Exclusive lock and an open transaction that my session needs to wait on. The only possible explanation (that I can come up with) is that this other session is locking the same row I am trying to update – which doesn’t make a whole lot of sense as the row is very user specific and multiple sessions updating a single user shouldn’t happen in this application.</p>
<p>The other confusing part is that this lock is being held for long enough to put a warning in the log file (>1 sec) and this update should run pretty much instantaneously. Also, the locking session ran fast as it didn’t display any DURATION line which is also set to a 1 sec threshold.</p>
<p>Enough guessing – I took my findings to the developers and together we eventually discovered a scheduled process that batch up requests to update these user rows, and it was possible for duplicate requests of the same rows to be run across multiple parallel sessions. The way it works indicated that many updates could be performed before it would commit, which can explain why my blocked update had to wait so long.</p>
<p>Timeline:</p>
<table border="1" cellspacing="0" cellpadding="0">
<tbody>
<tr>
<td width="130" valign="top">Session 1</td>
<td width="255" valign="top">Session 2</td>
</tr>
<tr>
<td width="130" valign="top">Begin</td>
<td width="255" valign="top">Begin</td>
</tr>
<tr>
<td width="130" valign="top">Update row A</td>
<td width="255" valign="top">&nbsp;</td>
</tr>
<tr>
<td width="130" valign="top">Update row B</td>
<td width="255" valign="top">Update row A (transaction share lock)</td>
</tr>
<tr>
<td width="130" valign="top">Update row C</td>
<td width="255" valign="top">Waiting</td>
</tr>
<tr>
<td width="130" valign="top">Update row D</td>
<td width="255" valign="top">Waited too long > log</td>
</tr>
<tr>
<td width="130" valign="top">Update row E</td>
<td width="255" valign="top">Waiting</td>
</tr>
<tr>
<td width="130" valign="top">Commit</td>
<td width="255" valign="top">Acquired lock > log</td>
</tr>
<tr>
<td width="130" valign="top">&nbsp;</td>
<td width="255" valign="top">Commit</td>
</tr>
</tbody>
</table>
<p>So only session 2 writes stuff to the log which is exactly what I was seeing.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.kimiensoftware.com/2011/07/debugging-sharelock-on-transaction-363/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>VACUUM Locks</title>
		<link>http://blog.kimiensoftware.com/2011/06/vacuum-locks-358</link>
		<comments>http://blog.kimiensoftware.com/2011/06/vacuum-locks-358#comments</comments>
		<pubDate>Thu, 30 Jun 2011 01:09:43 +0000</pubDate>
		<dc:creator>Nathan Thom</dc:creator>
				<category><![CDATA[PostgreSQL]]></category>
		<category><![CDATA[Analyze]]></category>
		<category><![CDATA[autovacuum]]></category>
		<category><![CDATA[Locking]]></category>
		<category><![CDATA[Vacuum]]></category>

		<guid isPermaLink="false">http://blog.kimiensoftware.com/?p=358</guid>
		<description><![CDATA[I’ve had some difficulty lately in understanding some locking activity going on in my databases, so I decided to run some tests to better understand how things work (using an [...]]]></description>
			<content:encoded><![CDATA[<p>I’ve had some difficulty lately in understanding some locking activity going on in my databases, so I decided to run some tests to better understand how things work (using an 8.3 server). Specifically – I want to know how the autovacuum process does or doesn’t affect sessions so I can rule it out from my investigations.</p>
<p>Session 1 – run a VACUUM on a large table (so it takes a while)</p>
<pre class="brush: sql; title: ; notranslate">mydb=# vacuum big_table;</pre>
<p>Session 2 – Update some rows in the table</p>
<pre class="brush: sql; title: ; notranslate">mydb=# begin;
BEGIN
mydb=# update big_table set cola = 'x' where id = 123456789;
UPDATE 112
</pre>
<p>Session 3 – Examine pg_locks</p>
<p>This is the VACUUM session:</p>
<pre class="brush: sql; title: ; notranslate">mydb=# select * from pg_locks where pid=2136;
  locktype  | database | relation | page | tuple | virtualxid | transactionid | classid | objid | objsubid | virtualtransaction | pid  |           mode           | granted
------------+----------+----------+------+-------+------------+---------------+---------+-------+----------+--------------------+------+--------------------------+---------
 relation   | 25693263 | 27681060 |      |       |            |               |         |       |          | 118/92993          | 2136 | RowExclusiveLock         | t
 relation   | 25693263 | 27681056 |      |       |            |               |         |       |          | 118/92993          | 2136 | RowExclusiveLock         | t
 relation   | 25693263 | 27679696 |      |       |            |               |         |       |          | 118/92993          | 2136 | ShareUpdateExclusiveLock | t
 virtualxid |          |          |      |       | 118/92993  |               |         |       |          | 118/92993          | 2136 | ExclusiveLock            | t
 relation   | 25693263 | 27681058 |      |       |            |               |         |       |          | 118/92993          | 2136 | RowExclusiveLock         | t
 relation   | 25693263 | 27681059 |      |       |            |               |         |       |          | 118/92993          | 2136 | RowExclusiveLock         | t
(6 rows)
</pre>
<p>So the VACUUM has taken a ShareUpdateExclusiveLock on the table and a number of RowExclusiveLock – one for each index.</p>
<p>This is the UPDATE session:</p>
<pre class="brush: sql; title: ; notranslate">mydb=# select * from pg_locks where pid=20666;
   locktype    | database | relation | page | tuple | virtualxid | transactionid | classid | objid | objsubid | virtualtransaction |  pid  |       mode       | granted
---------------+----------+----------+------+-------+------------+---------------+---------+-------+----------+--------------------+-------+------------------+---------
 relation      | 25693263 | 27681056 |      |       |            |               |         |       |          | 98/115834          | 20666 | RowExclusiveLock | t
 relation      | 25693263 | 27679696 |      |       |            |               |         |       |          | 98/115834          | 20666 | RowExclusiveLock | t
 virtualxid    |          |          |      |       | 98/115834  |               |         |       |          | 98/115834          | 20666 | ExclusiveLock    | t
 relation      | 25693263 | 27681060 |      |       |            |               |         |       |          | 98/115834          | 20666 | RowExclusiveLock | t
 transactionid |          |          |      |       |            |     219901739 |         |       |          | 98/115834          | 20666 | ExclusiveLock    | t
 relation      | 25693263 | 27681059 |      |       |            |               |         |       |          | 98/115834          | 20666 | RowExclusiveLock | t
 relation      | 25693263 | 27681058 |      |       |            |               |         |       |          | 98/115834          | 20666 | RowExclusiveLock | t
(7 rows)
</pre>
<p>The UPDATE has an Exclusive Lock on its virtual transaction id (<a href="http://www.postgresql.org/docs/current/static/view-pg-locks.html">which every session does</a>) and since it actually updated some rows, it also has an Exclusive Lock on a real transaction id. It also took Exclusive Row locks on the table and three indexes. Note that none of the locks are waiting, so there are no blocking issues here.</p>
<p>In other words – a VACUUM does not block an UPDATE. This is actually what I expected from looking at <a href="http://www.postgresql.org/docs/current/static/explicit-locking.html">this table</a> in the documentation:</p>
<table border="1">
<colgroup>
<col></col>
<col title="lockst" width="1*"></col>
<col></col>
<col></col>
<col></col>
<col></col>
<col></col>
<col></col>
<col title="lockend" width="1*"></col>
</colgroup>
<thead>
<tr>
<th rowspan="2">Requested Lock Mode</th>
<th colspan="8">Current Lock Mode</th>
</tr>
<tr>
<th>ACCESS SHARE</th>
<th>ROW SHARE</th>
<th>ROW EXCLUSIVE</th>
<th>SHARE UPDATE EXCLUSIVE</th>
<th>SHARE</th>
<th>SHARE ROW EXCLUSIVE</th>
<th>EXCLUSIVE</th>
<th>ACCESS EXCLUSIVE</th>
</tr>
</thead>
<tbody>
<tr>
<td>ACCESS SHARE</td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER">X</td>
</tr>
<tr>
<td>ROW SHARE</td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
</tr>
<tr>
<td>ROW EXCLUSIVE</td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
</tr>
<tr>
<td>SHARE UPDATE EXCLUSIVE</td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
</tr>
<tr>
<td>SHARE</td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER"></td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
</tr>
<tr>
<td>SHARE ROW EXCLUSIVE</td>
<td align="CENTER"></td>
<td align="CENTER"></td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
</tr>
<tr>
<td>EXCLUSIVE</td>
<td align="CENTER"></td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
</tr>
<tr>
<td>ACCESS EXCLUSIVE</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
<td align="CENTER">X</td>
</tr>
</tbody>
</table>
]]></content:encoded>
			<wfw:commentRss>http://blog.kimiensoftware.com/2011/06/vacuum-locks-358/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>PostgreSQL Tuning: join_collapse_limit is equivalent to Oracle&#8217;s ordered hint</title>
		<link>http://blog.kimiensoftware.com/2011/06/postgresql-tuning-join_collapse_limit-equivalent-to-oracle-ordered-hint-354</link>
		<comments>http://blog.kimiensoftware.com/2011/06/postgresql-tuning-join_collapse_limit-equivalent-to-oracle-ordered-hint-354#comments</comments>
		<pubDate>Wed, 29 Jun 2011 02:36:49 +0000</pubDate>
		<dc:creator>Nathan Thom</dc:creator>
				<category><![CDATA[PostgreSQL]]></category>
		<category><![CDATA[Analyze]]></category>
		<category><![CDATA[Explain]]></category>
		<category><![CDATA[Hints]]></category>
		<category><![CDATA[join_collapse_limit]]></category>
		<category><![CDATA[Performance]]></category>
		<category><![CDATA[Tuning]]></category>

		<guid isPermaLink="false">http://blog.kimiensoftware.com/?p=354</guid>
		<description><![CDATA[I had a fairly simple query that was running slow (165 secs) which I needed to tune: The first thing I noticed was the huge IN list of over 32,000 [...]]]></description>
			<content:encoded><![CDATA[<p>I had a fairly simple query that was running slow (165 secs) which I needed to tune:</p>
<pre class="brush: sql; title: ; notranslate">SELECT id
FROM property_vw
WHERE id IN (list of approx 32K numbers)
AND baths in ('2')
AND beds in ('2', '3')
AND property_type = 'UNIT'
ORDER BY a, few, columns;
</pre>
<p>The first thing I noticed was the huge IN list of over 32,000 Ids. Frankly, I’m amazed that PostgreSQL even accepts such a query and doesn’t spit out an error message immediately.</p>
<p>The explain analyze for this query is:<br />
(<a href="http://explain.depesz.com/s/mtm">anonymised and colorised via Depesz&#8217;s awesome online explain tool</a>)</p>
<pre class="brush: plain; title: ; notranslate">
Sort  (cost=655585.950..655585.950 rows=1 width=81) (actual time=165765.458..165765.629 rows=2432 loops=1)
    Sort Key: quebec_three.romeo_seven, quebec_three.mike_five, quebec_three.yankee_india, quebec_three.quebec_five, quebec_three.six_bravo, quebec_three.romeo_india, quebec_three.five, (lima_sierra(quebec_three.six_mike, 0)), (lima_sierra(quebec_three.charlie_hotel, ''alpha''::six_delta mike_seven))
    Sort Method:  quicksort  Memory: 439kB
  ->  Nested Loop  (cost=0.000..655585.940 rows=1 width=81) (actual time=22.486..165732.870 rows=2432 loops=1)
        ->  Nested Loop Left Join  (cost=0.000..655576.530 rows=1 width=32) (actual time=22.473..165713.367 rows=2432 loops=1)
                Join Filter: (lima_four.three_alpha = kilo.three_alpha)
              ->  Nested Loop  (cost=0.000..655568.090 rows=1 width=36) (actual time=22.461..165692.927 rows=2432 loops=1)
                    ->  Nested Loop  (cost=0.000..655566.960 rows=2 width=40) (actual time=22.451..165680.208 rows=2496 loops=1)
                          ->  Seq Scan on zulu_juliet zulu_kilo  (cost=0.000..627393.710 rows=567 width=4) (actual time=0.021..5377.204 rows=642599 loops=1)
                                  Filter: ((lima_sierra(((xray_xray -> 'six_kilo'::golf))::charlie_foxtrot, 0) = ANY ('oscar_victor'::charlie_foxtrot[])) AND (lima_sierra(((xray_xray -> 'tango'::golf))::charlie_foxtrot, 0) = 2))
                          ->  Index Scan using xray_five on six_alpha kilo  (cost=0.000..49.680 rows=1 width=36) (actual time=0.249..0.249 rows=0 loops=642599)
                                  Index Cond: (kilo.three_alpha = zulu_kilo.three_alpha)
                                  Filter: (kilo.three_alpha = ANY ('three_india'::charlie_foxtrot[]))
                    ->  Index Scan using india on oscar_seven xray_sierra  (cost=0.000..0.550 rows=1 width=4) (actual time=0.004..0.004 rows=1 loops=2496)
                            Index Cond: (xray_sierra.oscar_juliet = kilo.oscar_juliet)
                            Filter: (xray_sierra.victor_echo = 'zulu_echo'::golf)
              ->  Index Scan using four on victor_yankee lima_four  (cost=0.000..8.430 rows=1 width=8) (actual time=0.007..0.007 rows=1 loops=2432)
                      Index Cond: (lima_four.seven = kilo.three_sierra)
        ->  Index Scan using whiskey on yankee_zulu quebec_three  (cost=0.000..9.390 rows=1 width=57) (actual time=0.006..0.006 rows=1 loops=2432)
                Index Cond: (quebec_three.three_alpha = kilo.three_alpha)
</pre>
<p>It&#8217;s driving the query off an initial sequential scan of a large table. It&#8217;s estimating the scan will return 567 rows when in fact it returned 642599 rows. I can understand its limited ability to interpret the query when it has such a monster IN list. What I need is for the query to drive off an index lookup on a different table which is more selective.</p>
<p>Now I know what I want, but how to convince PostgreSQL that it&#8217;s the right choice?</p>
<p>So in Oracle, I would have tried adding an ORDERED hint (or more likely, a LEADING hint but then I wouldn’t have anything to compare with here!). However PostgreSQL does not support any hints, and most likely never will. What I did find in the PostgreSQL documentation is the join_collapse_limit query planner parameter:</p>
<p><em>&#8220;Setting it to 1 prevents any reordering of explicit JOINs. Thus, the explicit join order specified in the query will be the actual order in which the relations are joined.&#8221;</em></p>
<p>More info available in the <a href="http://www.postgresql.org/docs/current/static/explicit-joins.html">documentation</a>.</p>
<p>So join_collapse_limit seems to be the closest thing in PostgreSQL to the Oracle ordered hint. After setting this for my session:</p>
<pre class="brush: sql; title: ; notranslate">
set join_collapse_limit = 1;
</pre>
<p>I get the following new explain plan:<br />
(<a href="http://explain.depesz.com/s/Xa7">anonymised and colorised via Depesz&#8217;s awesome online explain tool</a>)</p>
<pre class="brush: plain; title: ; notranslate">
Sort  (cost=1526179.540..1526179.550 rows=1 width=81) (actual time=281.272..281.445 rows=2432 loops=1)
    Sort Key: quebec_three.romeo_seven, quebec_three.mike_five, quebec_three.yankee_india, quebec_three.quebec_five, quebec_three.six_bravo, quebec_three.romeo_india, quebec_three.five, (lima_sierra(quebec_three.six_mike, 0)), (lima_sierra(quebec_three.charlie_hotel, ''alpha''::six_delta mike_seven))
    Sort Method:  quicksort  Memory: 439kB
  ->  Nested Loop Left Join  (cost=90351.160..1526179.530 rows=1 width=81) (actual time=50.434..251.197 rows=2432 loops=1)
          Join Filter: (lima_four.three_alpha = kilo.three_alpha)
        ->  Nested Loop  (cost=90351.160..1526169.630 rows=1 width=85) (actual time=50.423..240.437 rows=2432 loops=1)
              ->  Nested Loop  (cost=90351.160..1526160.230 rows=1 width=36) (actual time=50.413..232.088 rows=2432 loops=1)
                    ->  Nested Loop  (cost=90351.160..1499651.650 rows=2878 width=32) (actual time=50.158..144.098 rows=23920 loops=1)
                          ->  Bitmap Heap Scan on six_alpha kilo  (cost=90351.160..1481550.430 rows=32209 width=36) (actual time=50.145..59.728 rows=32255 loops=1)
                                  Recheck Cond: (three_alpha = ANY ('victor_bravo'::charlie_foxtrot[]))
                                ->  Bitmap Index Scan on xray_five  (cost=0.000..90343.100 rows=32209 width=0) (actual time=49.636..49.636 rows=32255 loops=1)
                                        Index Cond: (three_alpha = ANY ('victor_sierra'::charlie_foxtrot[]))
                          ->  Index Scan using india on oscar_seven xray_sierra  (cost=0.000..0.550 rows=1 width=4) (actual time=0.002..0.002 rows=1 loops=32255)
                                  Index Cond: (xray_sierra.oscar_juliet = kilo.oscar_juliet)
                                  Filter: (xray_sierra.victor_echo = 'zulu_echo'::golf)
                    ->  Index Scan using papa on zulu_juliet zulu_kilo  (cost=0.000..9.200 rows=1 width=4) (actual time=0.003..0.003 rows=0 loops=23920)
                            Index Cond: (zulu_kilo.three_alpha = kilo.three_alpha)
                            Filter: ((lima_sierra(((zulu_kilo.xray_xray -> 'six_kilo'::golf))::charlie_foxtrot, 0) = ANY ('oscar_victor'::charlie_foxtrot[])) AND (lima_sierra(((zulu_kilo.xray_xray -> 'tango'::golf))::charlie_foxtrot, 0) = 2))
              ->  Index Scan using whiskey on yankee_zulu quebec_three  (cost=0.000..9.390 rows=1 width=57) (actual time=0.003..0.003 rows=1 loops=2432)
                      Index Cond: (quebec_three.three_alpha = kilo.three_alpha)
        ->  Index Scan using four on victor_yankee lima_four  (cost=0.000..9.890 rows=1 width=8) (actual time=0.003..0.004 rows=1 loops=2432)
                Index Cond: (lima_four.seven = kilo.three_sierra)
</pre>
<p>Which ran in only 281ms. Considering all the single page index lookups, I think this is quite fast.</p>
<p>I’m not happy with this solution though, as the view that is being queried has several other views inside it. If any of them were modified to join tables in a different order, the query would stop working again. Manually rewriting the views to make the query reference all tables would reduce the risk of this query breaking again, but of course you lose the benefit of having the views in the first place which is to encapsulate some of the complex logic from any calling queries.</p>
]]></content:encoded>
			<wfw:commentRss>http://blog.kimiensoftware.com/2011/06/postgresql-tuning-join_collapse_limit-equivalent-to-oracle-ordered-hint-354/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Drop schema dependency errors</title>
		<link>http://blog.kimiensoftware.com/2011/06/drop-schema-dependency-errors-351</link>
		<comments>http://blog.kimiensoftware.com/2011/06/drop-schema-dependency-errors-351#comments</comments>
		<pubDate>Fri, 24 Jun 2011 06:49:14 +0000</pubDate>
		<dc:creator>Nathan Thom</dc:creator>
				<category><![CDATA[PostgreSQL]]></category>
		<category><![CDATA[schema]]></category>

		<guid isPermaLink="false">http://blog.kimiensoftware.com/?p=351</guid>
		<description><![CDATA[I needed to drop a schema that was created for debugging purposes and I knew it had no relationships with other objects outside of that schema (PostgreSQL v8.3.6). Looking closely, [...]]]></description>
			<content:encoded><![CDATA[<p>I needed to drop a schema that was created for debugging purposes and I knew it had no relationships with other objects outside of that schema (PostgreSQL v8.3.6).</p>
<pre class="brush: sql; title: ; notranslate">mydb=# DROP SCHEMA foobar;
NOTICE:  view foobar.vendors depends on schema foobar
NOTICE:  rule _RETURN on view foobar.vendors depends on view foobar.vendors
NOTICE:  table foobar.transfer_types depends on schema foobar
NOTICE:  view foobar.suggest depends on schema foobar
NOTICE:  sequence foobar.auction_results_auction_results_poid_seq depends on schema foobar
NOTICE:  default for table foobar.auction_results column auction_results_poid depends on sequence foobar.auction_results_auction_results_poid_seq
NOTICE:  function foobar.array_median(numeric[]) depends on schema foobar
&lt;snip>
ERROR:  cannot drop schema foobar because other objects depend on it
HINT:  Use DROP ... CASCADE to drop the dependent objects too.
</pre>
<p>Looking closely, I notice that every single problem it highlighted was a dependency of something in that schema with something else within that same schema. So&#8230; if I’m dropping the entire schema why are you complaining about it?</p>
<p>Of course it’s easily fixed by using cascade, but I don’t like stupid error messages.</p>
<pre class="brush: sql; title: ; notranslate">mydb=# drop SCHEMA foobar cascade;
NOTICE:  Blah blah lots of whiney crap here blah blah
DROP SCHEMA
</pre>
]]></content:encoded>
			<wfw:commentRss>http://blog.kimiensoftware.com/2011/06/drop-schema-dependency-errors-351/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>

