Member Junction
    Preparing search index...
    • Read-only enforcement for the native-query path (RunNativeQuery).

      External Data Sources are read-only by contract, but a stored Query's fully-rendered SQL is executed verbatim on a read/write connection. The provider-layer write backstop and ReadOnlyExternalBaseEntity only cover Save/Delete — they do NOT see this path — so the guarantee is enforced HERE, at the driver/engine boundary, not delegated to a caller.

      The text is read with the source dialect's own lexical rules (MySQL # comments and its ---needs-whitespace rule, backticks, backslash escapes, Snowflake $$ strings and // comments, Oracle q'…' literals, …). Fail-closed. Throws when the SQL:

      • contains a comment the database runs (MySQL /*! … */), or a backslash in a string literal on a dialect where a server setting decides what a backslash means,
      • contains multiple/stacked statements (injection / smuggled write),
      • starts with a DCL verb (GRANT/REVOKE/DENY) after any leading comments,
      • cannot be parsed in the dialect's node-sql-parser grammar, contains any write/DDL statement at any depth, is a SELECT ... INTO, or is not exactly one typed statement; or, for a dialect without a grammar (Oracle), is not a single SELECT/WITH free of write keywords.

      Known limitation — defense-in-depth, NOT a substitute for a least-privilege source credential:

      • A side-effecting routine invoked from a read shape (SELECT writing_func(), SELECT nextval('s')) is indistinguishable from a pure read in the AST and is NOT blocked. Configure External Data Sources with a read-only/least-privilege credential as the real authority; this screen is the app-level backstop against the common write/DDL/injection vectors.

      Parameters

      Returns void