| From: | Shinya Kato <shinya11(dot)kato(at)gmail(dot)com> |
|---|---|
| To: | Fujii Masao <masao(dot)fujii(at)gmail(dot)com> |
| Cc: | Chao Li <li(dot)evan(dot)chao(at)gmail(dot)com>, PostgreSQL-development <pgsql-hackers(at)postgresql(dot)org> |
| Subject: | Re: file_fdw: Support multi-line HEADER option. |
| Date: | 2026-01-20 04:16:33 |
| Message-ID: | CAOzEurSE095pGSx1dka7Qxggdc9HtreOUY7RK7PxT-ODXr+rtA@mail.gmail.com |
| Views: | Whole Thread | Raw Message | Download mbox | Resend email |
| Thread: | |
| Lists: | pgsql-hackers |
On Mon, Jan 19, 2026 at 8:22 PM Fujii Masao <masao(dot)fujii(at)gmail(dot)com> wrote:
> +CREATE FOREIGN TABLE tbl () SERVER file_server OPTIONS (header
> '2.5'); -- ERROR
> +ERROR: header requires a Boolean value, a non-negative integer, or
> the string "match"
>
> This isn't caused by the patch, but I think the error message itself should
> be improved in a separate patch before adding multi-line header support
> to file_fdw. Per the Error Message Style Guide, "non-negative" should
> be avoided because it's ambiguous about whether zero is accepted.
I didn't know such a style guide, thanks. I've fixed it in the v4-0001 patch.
> - syntax requires a value to be present in all cases. To activate
> - <command>COPY</command> options typically written without a value,
> you can pass
> - the value TRUE, since all such options are Booleans.
> + syntax requires a value to be present in all cases. Use the appropriate
> + explicit value (for example <literal>TRUE</literal>,
> <literal>match</literal>,
> + or a non-negative integer line count for <literal>HEADER</literal>) to enable
> + the desired behavior.
>
> Using "non-negative" here has the same ambiguity.
>
> I'm not sure if this change is an improvement. Isn't the original wording
> almost OK? Of course, "all such options are Booleans" is not true and
> probably should be something like "all such options accpet Boolean values",
> though.
I've fixed it as suggested.
> + if (IsA(def->arg, Integer))
> + return defCheckCopyHeaderInteger(def, intVal(def->arg), is_from);
> + else
> + return defCheckCopyHeaderString(def, defGetString(def), is_from);
>
> Personally, I think it would be simpler and easier to understand to keep
> the logic in a single function defGetCopyHeaderOption(), rather than
> splitting it across three functions. Thought?
>
> For example,
> -------------------------------------
> switch (nodeTag(def->arg))
> {
> case T_Integer:
> ival = intVal(def->arg);
> break;
> default:
> {
> char *sval = defGetString(def);
>
> ...
>
> else
> {
> ErrorSaveContext escontext = {T_ErrorSaveContext};
>
> /* Check if the header is a valid integer */
> ival = pg_strtoint32_safe(sval, (Node *) &escontext);
> if (escontext.error_occurred)
> ereport(ERROR,
> (errcode(ERRCODE_SYNTAX_ERROR),
> errmsg("%s requires a Boolean value,
> a non-negative integer, "
> "or the string \"match\"",
> def->defname)));
> }
> }
> break;
> }
>
> if (ival < 0)
> ereport(ERROR,
> (errcode(ERRCODE_INVALID_PARAMETER_VALUE),
> errmsg("a negative integer value cannot be "
> "specified for %s", def->defname)));
>
> ...
> -------------------------------------
Thank you! I was struggling with how to write it cleanly, but the code
you suggested is clear and easy to understand.
--
Best regards,
Shinya Kato
NTT OSS Center
| Attachment | Content-Type | Size |
|---|---|---|
| v4-0001-Replace-non-negative-with-greater-than-or-equal-t.patch | application/octet-stream | 3.7 KB |
| v4-0002-file_fdw-Support-multi-line-HEADER-option.patch | application/octet-stream | 12.7 KB |
| From | Date | Subject | |
|---|---|---|---|
| Next Message | Amit Kapila | 2026-01-20 04:17:18 | Re: Logical Replication of sequences |
| Previous Message | Amit Kapila | 2026-01-20 03:57:30 | Re: Logical Replication of sequences |