DapperLib / DapperLib/Dapper

Postgres type cast is interpreted as parameter

Open
#1,299 0 comments 0 reactions 0 assignees View on GitHub

Nobody has claimed this yet.

Dominant language
C#
Stars
18.4k
Forks
3.7k
Avg merge
5h 8m
Merged PRs (30d)
1

Description

In Postgres type casting is performed via value::type. When calling ExecuteAsync or QueryAsync with parameters Dapper (sometimes) interprets the : as parameter key and as a consequence throws an System.ArgumentNullException.

This is not always the case and guessing from the type name this only occurs when the type name (the casting type) is a partial match with parameters passed in to the method.

Here is a snippet of the code which is throwing an exception.

var sql = @"
    INSERT INTO
        public.table (id, title, status)
    VALUES
        (
            @Id,
            @TitleText,
            (@StatusText)::ad_item_status
        )";

using (var connection = new NpgsqlConnection())
{
    await connection.ExecuteAsync(new CommandDefinition(sql, item, cancellationToken: token));
}

The item does contain a property with the name 'item.Status' which may be related to the problem. As far as I can see there is not an option to disable to ; and ? parameter prefixes from being interpreted.

Stacktrace

at System.Reflection.Emit.DynamicILGenerator.Emit(OpCode opcode, MethodInfo meth)
at Dapper.SqlMapper.CreateParamInfoGenerator(Identity identity, Boolean checkForDuplicates, Boolean removeUnused, IList`1 literals) in C:\projects\dapper\Dapper\SqlMapper.cs:line 2575
at Dapper.SqlMapper.GetCacheInfo(Identity identity, Object exampleParameters, Boolean addToCache) in C:\projects\dapper\Dapper\SqlMapper.cs:line 1707
at Dapper.SqlMapper.ExecuteMultiImplAsync(IDbConnection cnn, CommandDefinition command, IEnumerable multiExec) in C:\projects\dapper\Dapper\SqlMapper.Async.cs:line 646

The workaround is straightforward as Postgres also supports the CAST ('value' AS type) syntax, but this is much harder to read. FWIW: The casting does work since I cast regular to JSON via value::jsonb without any issues.

PS. I could not find any similar issues with NpgSQL in Dapper.

Contributor guide

No contributing guide indexed for this repository

First steps

  1. Read the whole issue, then the project's contributing guide.
  2. Comment on the issue to say you are picking it up — it saves two people doing the same work.
  3. Fork the repository and make your change on a branch.
  4. Open a pull request that references the issue number.

Research direction

Start in Dapper.SqlMapper.CreateParamInfoGenerator, referenced from Dapper/SqlMapper.cs, and reproduce the ExecuteAsync or QueryAsync case using the shown PostgreSQL ::ad_item_status cast and parameters. Verify that a regression test covers partial matches between cast type names and parameter names, while existing value::jsonb behavior remains unaffected.

Written by the indexing model from the issue text.

Assessment

Tech stack
csharp, postgresql
Domain
database
Issue type
Bug
Difficulty
3/5
Estimated time
1-2 days
Activity status
Stale
Clarity
Mostly clear
Newbie friendliness
45/100

Get new issues in your inbox

A short digest of beginner-friendly GitHub issues.