Subject: Re: CREATE TABLE LIKE INCLUDING POLICIES

From: jian he <[email-masked]>
Date: Thu, 22 Jan 2026 13:45:54 +0800

On Wed, Jan 21, 2026 at 11:23 PM Zsolt Parragi
<[email-masked]> wrote:
>
> Hello!
>
> Generally looks good to me, the tests work, the new feature seem to
> work, I only noticed a few minor things.
>
> parse_utilcmd.c:2204
> + ereport(ERROR,
> + errcode(ERRCODE_FEATURE_NOT_SUPPORTED),
> + errmsg("cannot convert whole-row table reference"),
> + errdetail("Security policy \"%s\" contains a whole-row reference to
> table \"%s\".",
> +   NameStr(policy_form->polname),
> +   RelationGetRelationName(parent_rel)));
>
> The outer parentheses are missing after "ERROR, "
>
> Same issue at line 2232.

Actually, this extra parentheses is optional.
see
https://postgr.es/m/[email-masked]
and
https://postgr.es/m/[email-masked]

>
> parse_utilcmd:1634
> + policy_form = (Form_pg_policy) GETSTRUCT(tuple);
> +
> + polrels = PolicyGetRelations(policy_form->oid);
>
> Shouldn't the function free polrels after the foreach below?
>

I found this post
https://stackoverflow.com/questions/79672060/when-should-i-use-pfree-in-a-postgres

I noticed that the above RelationGetIndexList does not list_free
parent_indexes as well.
It should be ok not not call list_free polrels too, because as the memory
allocation here is in portal context which should be reset by end of the current
statement execution.

> policy.c:1357
> +
> + relation_close(depRel, AccessShareLock);
> +
>
> Shouldn't that be table_close?
>
> create_table.sgml:760
> +          All row-level security policies are copied to the new table.
> +          Note that by default row-level security is not enabled to
> the new table,
> +          using <command>ALTER TABLE ... ENABLE ROW LEVEL SECURITY</command>
> +          in order for created policies to be applied to the new table.
>
> Maybe "use ALTER TABLE ... ENABLE ROW LEVEL SECURITY to copy existing
> policies to the new table"?
>
how about

+ All row-level security policies are copied to the new table.
+ Note, however, that row-level security policies are not enabled on the new
+ table by default,
+ using <command>ALTER TABLE ... ENABLE ROW LEVEL SECURITY</command>
+ for the copied policies to take effect.

> I am also wondering if this shouldn't be at least an option for CREATE
> TABLE AS. This seems like something that's very easy to overlook and
> accidentally forget.

do you mean
https://www.postgresql.org/docs/current/sql-createtableas.html
to also copy RLS policies.
if so, seems not doable, for example,

create table x as select from tenk1, tenk2 limit 2;

Should it copy all RLS policies from tenk1 and tenk2 to the new tables?
That does not seem to make sense to me.

--
jian
https://www.enterprisedb.com/