Skip to content

Generated SQL identifiers should escape embedded quote characters #16

@akshithg

Description

@akshithg

Summary

borp's dialect identifier quoting helpers wrap identifiers in dialect quote
characters but do not escape embedded quote characters. Mapper metadata such as
table, column, schema, or index names can therefore break out of the quoted
identifier and change generated SQL.

Affected area

Tested on main at c0288adf3b533244dd2bf2fca08ca4418b25d281.

Affected helpers:

  • SqliteDialect.QuoteField
  • PostgresDialect.QuoteField
  • MySQLDialect.QuoteField
  • QuotedTableForQuery callers
  • generated DML and index DDL paths

Reproduction

With SQLite, register a mapped table name containing an embedded quote:

victim" SET admin = 1 WHERE ? <> ? --

Before escaping, generated update SQL can become:

update "victim" SET admin = 1 WHERE ? <> ? -- " set "ID"=?, "Value"=? where "ID"=?;

A focused regression shows this changes victim.admin from 0 to 1 through
the mapped table name.

Expected behavior

Identifier metadata should either be rejected or escaped so it cannot change
generated SQL structure.

Actual behavior

QuoteField concatenates the opening quote, raw identifier, and closing quote.
Embedded dialect quote characters terminate the quoted identifier.

Impact

This is a SQL injection surface for downstream consumers that let external input
influence mapper metadata. I did not find a Boulder path where external input
controls borp mapper metadata; the affected surface is borp library consumers
that do expose that kind of mapping.

Suggested fix

Escape the dialect-specific identifier quote character:

  • SQLite/PostgreSQL: double embedded " characters.
  • MySQL: double embedded backticks.

Add regression coverage for DML generated from table metadata and DDL generated
from index, schema, and table metadata.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type
    No fields configured for issues without a type.

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions