Received: from maia.hub.org (maia-3.hub.org [200.46.204.243]) by mail.postgresql.org (Postfix) with ESMTP id D6B441337CDD for ; Wed, 27 Apr 2011 17:25:47 -0300 (ADT) Received: from mail.postgresql.org ([200.46.204.86]) by maia.hub.org (mx1.hub.org [200.46.204.243]) (amavisd-maia, port 10024) with ESMTP id 46549-04-7 for ; Wed, 27 Apr 2011 20:25:40 +0000 (UTC) X-Greylist: domain auto-whitelisted by SQLgrey-1.7.6 Received: from lo.gmane.org (lo.gmane.org [80.91.229.12]) by mail.postgresql.org (Postfix) with ESMTP id 3E7A01337E04 for ; Wed, 27 Apr 2011 17:17:33 -0300 (ADT) Received: from list by lo.gmane.org with local (Exim 4.69) (envelope-from ) id 1QFBAu-0005GZ-Kd for pgsql-admin@postgresql.org; Wed, 27 Apr 2011 22:17:28 +0200 Received: from frigga.summersault.com ([12.161.105.138]) by main.gmane.org with esmtp (Gmexim 0.1 (Debian)) id 1AlnuQ-0007hv-00 for ; Wed, 27 Apr 2011 22:17:28 +0200 Received: from mark by frigga.summersault.com with local (Gmexim 0.1 (Debian)) id 1AlnuQ-0007hv-00 for ; Wed, 27 Apr 2011 22:17:28 +0200 X-Injected-Via-Gmane: http://gmane.org/ To: pgsql-admin@postgresql.org From: Mark Stosberg Subject: Re: best practice for moving millions of rows to child table when setting up partitioning? Date: Wed, 27 Apr 2011 16:17:16 -0400 Lines: 51 Message-ID: References: Mime-Version: 1.0 Content-Type: text/plain; charset=ISO-8859-1 Content-Transfer-Encoding: 7bit X-Complaints-To: usenet@dough.gmane.org X-Gmane-NNTP-Posting-Host: frigga.summersault.com User-Agent: Mozilla/5.0 (X11; U; Linux i686; en-US; rv:1.9.2.14) Gecko/20110223 Thunderbird/3.1.8 In-Reply-To: X-Enigmail-Version: 1.1.1 X-Virus-Scanned: Maia Mailguard 1.0.1 X-Spam-Status: No, hits=-1.595 tagged_above=-10 required=5 tests=BAYES_00=-1.9, SARE_MILLIONSOF=0.315, T_RP_MATCHES_RCVD=-0.01 X-Spam-Level: X-Archive-Number: 201104/245 X-Sequence-Number: 37426 On 04/27/2011 10:48 AM, Mark Stosberg wrote: > > Hello, > > I'm working on moving a table with over 30 million to rows to be > partitioned. The table seeing several inserts per second. It's > essentially an activity log that only sees insert activity and is > lightly used for reporting, such that queries against it can safely be > disabled during a transition. > > I'm looking for recommendations for a way to do this that will be least > disruptive to the flow of inserts statements that will continue to > stream in. > > Here's the plan which seems best to me at the moment. Is it is > reasonable? I revised my plan based on feedback and mentioned resources here, and also due to my own concerns about the resource and performance impact of using the INSERT .. SELECT pattern on millions of rows at a time. Here's my revised plan for the transition, which avoids using large INSERT..SELECT statements, and only requires a minimal amount of the transition to work to happen once the application has started to insert data into the child tables. Seem reasonable? New Plan --------- 1. Create the child tables targeted to contain data from the parent as standalone tables (including archive tables and the current month). 2. Take a full database backup from this morning and extract the COPY statement for the parent table. Manually split it up by date to create multiple copy statements, one for each partition. 3. Run the COPY statements to load the data into each child table. So far, everything has happened outside of application access. 4. Find the max ID that has been inserted in the current child table. 5. INSERT .. SELECT the missing rows from the last backup from the parent table to the current child table to be. Again, note the max ID. 6. Now, during a maintenance window: - alter the child tables to inherit the parent - Set up the trigger which starts redirecting inserts from the parent table to the child table. - INSERT .. SELECT the file the final few missing rows from the parent to the current child - TRUNCATE then CLUSTER the parent table.