Received: from malur.postgresql.org ([217.196.149.56]) by arkaria.postgresql.org with esmtp (Exim 4.84_2) (envelope-from ) id 1e0XCZ-0005M3-M6 for pgsql-hackers@arkaria.postgresql.org; Fri, 06 Oct 2017 18:18:23 +0000 Received: from localhost ([127.0.0.1] helo=postgresql.org) by malur.postgresql.org with smtp (Exim 4.84_2) (envelope-from ) id 1e0XCZ-000133-8l for pgsql-hackers@arkaria.postgresql.org; Fri, 06 Oct 2017 18:18:23 +0000 Received: from makus.postgresql.org ([2001:4800:1501:1::229]) by malur.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA384:256) (Exim 4.84_2) (envelope-from ) id 1e0XCX-00011D-T3 for pgsql-hackers@postgresql.org; Fri, 06 Oct 2017 18:18:22 +0000 Received: from mail-lf0-x243.google.com ([2a00:1450:4010:c07::243]) by makus.postgresql.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_CBC_SHA1:256) (Exim 4.84_2) (envelope-from ) id 1e0XCU-0003jI-Lj for pgsql-hackers@postgresql.org; Fri, 06 Oct 2017 18:18:20 +0000 Received: by mail-lf0-x243.google.com with SMTP id d17so21296339lfe.2 for ; Fri, 06 Oct 2017 11:18:18 -0700 (PDT) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gmail.com; s=20161025; h=subject:to:cc:references:from:message-id:date:user-agent :mime-version:in-reply-to:content-language; bh=J5PaBZgmwGG+zTQOassjhdFknlR6hdV/jkuDsyWkUeQ=; b=q95iAcUiPdvxXpaLvyc4ca0ponovtDq+9B97CYuCstXIYAG5tOkEvBFlGRUcAXr9CS HJoQezOdawolh7WKWoILn9OlnfTmLVlMP5AGZa8mU7Ozd0HOnO+tjwNohIKZap2Go77D eDwBY5vbMlRwhKvfZlJa+RuTjdbAqAizqf/ddH9G3J7nuwUVXCbAtg0hnd6/+z6ntpU/ WOFFoVhiHc4SFL5BvGgg7B61nPomUjDlrAGFArnL/5Xl3dJ+q0Fa2XpUoSfm0Q+8LZS0 OO4Ej9jrv6D2CUKHbq5iueeJwZrPQoe/+/AmVzT7VQrI3+6yyamkQYXGwvkzZLWvO8f0 s4GQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20161025; h=x-gm-message-state:subject:to:cc:references:from:message-id:date :user-agent:mime-version:in-reply-to:content-language; bh=J5PaBZgmwGG+zTQOassjhdFknlR6hdV/jkuDsyWkUeQ=; b=fNi9rZ3qaD/r+PxmFy2XMeQbHExoYppgw41QgR7mfrP8ivQJrfOroor0wDvs1KcbJ+ 4NZ7lKQkuyr5lzKpXVkoPFMYgs/rRPembOYruXXk6Axya+E9SMQqFRxG8WZ4/ffVivcj ghqjbwgQQwr1hOkQaQRJ0cYjvirfhgaQFFi1ULtcwY7Xa/i/hMx7fkamvAK48v/koN3O 9cKmCqkJ5z80Bn77gtbpxz7TIML8hN1KWfDocSgFW6E7J+kxdsFNDWT3oaXpaAo7CgE+ LABCauzLD1P4tJ62tGpkLsc75yDuG2sGOEev9UGcrqWEoLOtJVYOD2dPZuVBDa5fX8ib OTPg== X-Gm-Message-State: AMCzsaWlSrWDEW7iVyf+MNf3TRRkeh/4HmTh0JFqDILJzk1SQTCPpU3y ZJneWYVkYPT96YXcuEmiX/BRv2b+ X-Google-Smtp-Source: AOwi7QBJf+afJaAMFe4TWr1z/Uoi4L/onMWNIxReYCEaGz+iyiA56yLCTKUiB+UIv9W58KrLH7dX1w== X-Received: by 10.25.26.14 with SMTP id a14mr1141945lfa.28.1507313896049; Fri, 06 Oct 2017 11:18:16 -0700 (PDT) Received: from [10.3.1.85] ([185.62.200.107]) by smtp.gmail.com with ESMTPSA id 1sm454697ljp.29.2017.10.06.11.18.14 (version=TLS1_2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128/128); Fri, 06 Oct 2017 11:18:14 -0700 (PDT) Subject: Re: Proposal: Local indexes for partitioned table To: Alvaro Herrera , Pg Hackers Cc: Maksim Milyutin References: <20171006163715.oulhmymknz3m5mqm@alvherre.pgsql> From: Maksim Milyutin Message-ID: <4df81bc5-538e-bd4e-1e9f-5ef249aff02c@gmail.com> Date: Fri, 6 Oct 2017 21:18:14 +0300 User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:52.0) Gecko/20100101 Thunderbird/52.3.0 MIME-Version: 1.0 In-Reply-To: <20171006163715.oulhmymknz3m5mqm@alvherre.pgsql> Content-Type: multipart/alternative; boundary="------------2CF9301CE3BE5EF80909515A" Content-Language: en-US List-Archive: List-Help: List-ID: List-Owner: List-Post: List-Subscribe: List-Unsubscribe: X-Mailing-List: pgsql-hackers Precedence: bulk Sender: pgsql-hackers-owner@postgresql.org This is a multi-part message in MIME format. --------------2CF9301CE3BE5EF80909515A Content-Type: text/plain; charset=utf-8; format=flowed Content-Transfer-Encoding: 7bit Hi! On 06.10.2017 19:37, Alvaro Herrera wrote: > As you propose, IMO this new feature would use the standard index > creation syntax: > CREATE [UNIQUE] INDEX someindex ON parted_table (a, b); > > This command currently throws an error. We'd have it do two things: > > 1. create catalog rows in pg_class and pg_index for the main table, > indicating the existance of this partitioned index. These would not > point to an actual index (since the main table itself is empty), but > instead to an "abstract" index. This abstract index can be used by > various operations; see below. Robert Haas proposed[1] to use the name "partitioned index" (instead of abstract) that have to be reflected in 'relkind' field of pg_class as the RELKIND_PARTITIONED_INDEX value. > I propose that an index declared UNIQUE throws an error for now. We can > implement uniqueness (for the case where the indexed columns match the > partitioning key) later, once we sort out all the issues here first. I > think unique indexes would be very useful even with that limitation, but > let's have it as a separate project. Yes, global uniqueness through local unique indexes causes further work related with foreign keys on partitioned table, full support of INSERT OF CONFLICT, etc. It make sense to implement after the current stage of work. > I think using pg_depend as the mechanism to link partition indexes to > parent is a bad idea. How about pg_inherits instead? Seems more > appropriate. Greg Stark proposed[2] to use new pg_index field of oid type that refers to the parent pg_index item. AFAIC pg_inherits also makes sense but semantically it deals with inheriting tables. IMHO the using of this catalog table to define relation between partitioned table and partitions looks like a hack to make use of constraint exclusion logic for partition pruning. > Creating hierachy-wide indexes for existing partitioned tables is likely > to take a long time, so we must include CONCURRENTLY as an option. This > will need some transaction machinery support in order to ensure that > each partition gets its index created at some point in a long chain of > transactions, and that the whole thing is marked valid only at the end. > Also, if the creation is interrupted (because of a crash or a regular > shutdown), it'll be useful to be able to continue rather than being > forced to start from scratch. This option was very difficult for me. I would be interested to see the implementation. > During ALTER TABLE ... ATTACH PARTITION, we check that an indexing > satisfying the abstract index exist (and we create a pg_inherit link). > If not, the command is aborted. We could create necessary index for partition, not abort ALTER TABLE ... ATTACH PARTITION statement. > We need to come up with some way to generate names for each partition > index. I think the calling 'ChooseIndexName(RelationGetRelationName(childrel), namespaceId, indexColNames, ...)' resolves this problem. > I am going to work on this now. It will be great! I think this project is difficult for me on the part of integration described above functionality with the legacy postgres code. Also IMO this project is very important because it opens the way for such feature as global uniqueness of fields of partitioned tables. And any protraction in implementation is bad. I would like to review and test your intermediate results. 1. https://www.postgresql.org/message-id/CA%2BTgmoY5UOUnW%3DMcwT7xUB_2W5dAkvOg5kD20Spx5gF-Ad47cA%40mail.gmail.com 2. https://www.postgresql.org/message-id/CAM-w4HOVftuv5RVi3a%2BsRV6nBpg204w7%3DL8MwPXVvYBFo1uM1Q%40mail.gmail.com -- Regards, Maksim Milyutin --------------2CF9301CE3BE5EF80909515A Content-Type: text/html; charset=utf-8 Content-Transfer-Encoding: 7bit

Hi!


On 06.10.2017 19:37, Alvaro Herrera wrote:
As you propose, IMO this new feature would use the standard index
creation syntax:
   CREATE [UNIQUE] INDEX someindex ON parted_table (a, b);

This command currently throws an error.  We'd have it do two things:

1. create catalog rows in pg_class and pg_index for the main table,
   indicating the existance of this partitioned index.  These would not
   point to an actual index (since the main table itself is empty), but
   instead to an "abstract" index.  This abstract index can be used by
   various operations; see below.

Robert Haas proposed[1] to use the name "partitioned index" (instead of abstract) that have to be reflected in 'relkind' field of pg_class as the RELKIND_PARTITIONED_INDEX value.

I propose that an index declared UNIQUE throws an error for now.  We can
implement uniqueness (for the case where the indexed columns match the
partitioning key) later, once we sort out all the issues here first.  I
think unique indexes would be very useful even with that limitation, but
let's have it as a separate project.

Yes, global uniqueness through local unique indexes causes further work related with foreign keys on partitioned table, full support of INSERT OF CONFLICT, etc. It make sense to implement after the current stage of work.

I think using pg_depend as the mechanism to link partition indexes to
parent is a bad idea.  How about pg_inherits instead?  Seems more
appropriate.

Greg Stark proposed[2] to use new pg_index field of oid type that refers to the parent pg_index item. AFAIC pg_inherits also makes sense but semantically it deals with inheriting tables. IMHO the using of this catalog table to define relation between partitioned table and partitions looks like a hack to make use of constraint exclusion logic for partition pruning.

Creating hierachy-wide indexes for existing partitioned tables is likely
to take a long time, so we must include CONCURRENTLY as an option.  This
will need some transaction machinery support in order to ensure that
each partition gets its index created at some point in a long chain of
transactions, and that the whole thing is marked valid only at the end.
Also, if the creation is interrupted (because of a crash or a regular
shutdown), it'll be useful to be able to continue rather than being
forced to start from scratch.

This option was very difficult for me. I would be interested to see the implementation.

During ALTER TABLE ... ATTACH PARTITION, we check that an indexing
satisfying the abstract index exist (and we create a pg_inherit link).
If not, the command is aborted.

We could create necessary index for partition, not abort ALTER TABLE ... ATTACH PARTITION statement.

We need to come up with some way to generate names for each partition
index.

I think the calling 'ChooseIndexName(RelationGetRelationName(childrel), namespaceId, indexColNames, ...)' resolves this problem.

I am going to work on this now.

It will be great! I think this project is difficult for me on the part of integration described above functionality with the legacy postgres code. Also IMO this project is very important because it opens the way for such feature as global uniqueness of fields of partitioned tables. And any protraction in implementation is bad.

I would like to review and test your intermediate results.


1. https://www.postgresql.org/message-id/CA%2BTgmoY5UOUnW%3DMcwT7xUB_2W5dAkvOg5kD20Spx5gF-Ad47cA%40mail.gmail.com
2. https://www.postgresql.org/message-id/CAM-w4HOVftuv5RVi3a%2BsRV6nBpg204w7%3DL8MwPXVvYBFo1uM1Q%40mail.gmail.com
-- 
Regards,
Maksim Milyutin
--------------2CF9301CE3BE5EF80909515A--