80 likes | 160 Views
Partitions not Working as Expected. By: Lloyd Albin 8/6/2013. The Problem. I found this issue posted on the pgsql -performance mailing list and decided to verify the problem since we use partitions in our database. http:// www.postgresql.org/message-id/51CC652F.3010304@optionshouse.com
E N D
Partitions not Workingas Expected By: Lloyd Albin 8/6/2013
The Problem I found this issue posted on the pgsql-performance mailing list and decided to verify the problem since we use partitions in our database. http://www.postgresql.org/message-id/51CC652F.3010304@optionshouse.com My tanks to Shaun for exposing this issue. Shaun ThomasOptionsHouse| 141 W. Jackson Blvd. | Suite 500 | Chicago IL, 60604312-676-8870sthomas(at)optionshouse(dot)com
Creating the tables We first create the parent table and then two child tables. The child tables have check constraints to limit what data may be added to the child table and to help the query optimizer to know if this table should be part of the query or not when querying the parent table. CREATE TABLE part_test ( fake INT, part_col TIMESTAMP WITHOUT TIME ZONE ); CREATE TABLE part_test_1 ( CHECK (part_col >= '2013-05-01' AND part_col < '2013-06-01') ) INHERITS (part_test); CREATE TABLE part_test_2 ( CHECK (part_col >= '2013-04-01' AND part_col < '2013-05-01') ) INHERITS (part_test);
Usage of the check constraint in your query If you hard code your date into your query, then it uses the correct child partition for your query. EXPLAIN SELECT * FROM part_test WHERE part_col > '2013-06-27';
The problem We find that where we think it should have used the correct child table, it instead use all the child tables, ignoring the check constraints. As a dba we tell the developers to use Postgres as much as possible instead of their programming language. EXPLAIN SELECT * FROM part_test WHERE part_col > CURRENT_DATE;
Additional issues While these were not tested/reported, they will also fail as I found out during my testing. SELECT * FROM part_test WHERE part_col > NOW(); SELECT * FROM part_test WHERE part_col > date_trunc(‘month’, NOW());
Talking about the issue. This is one of the many responses. This one by Tom Lane. The long and the short of the issue is that the DATE/TIME functions can change over time or even be different between when you prepare a statement and execute the statement so they will always scan all the child tables. I don't see any very good solution to your problem within the current approach to partitioning, which is basically theorem-proving. That proof engine has no concept of time passing, let alone the sort of detailed knowledge of the semantics of this particular function that would allow it to conclude "if CURRENT_DATE > '2013-06-20' is true now, it will always be so in the future as well".
The solution We all hate this solution for a fix for this will be a long ways off as they say the whole engine will have to be re-written to support a fix. The only current solution is to hard code your date/timestamp into your query where your programming language submits the current date/timestamp as a text string instead of using the system variables.