dapperを使ってたら「IConvertible を実装しなければなりません」

dapperを使用したDBアクセス処理をしたらIConvertibleを実装しろとエラーが出た。
なんの変哲も無いSelect処理でなぜ?という感じで解決するまで随分はまってしまったが、終わってみれば全くしょうもないミスだった。

原因

SQLでSelectしてる値の型がマッピング先のクラスと一致していないから

修正前コード

だいたいこんな感じで、Selectしてる値はuniqueidentifierだったのにマッピング先はStringにしていた。

public class DataAccessObject{
  private const string sql = @"
declare @id uniqueidentifier
exec something_procedure @parm, @id output
select @id as Id
";

  public string GetId(){
    using (var conn = My.ConnectionFactory())
    {
      return conn.QueryFirstOrDefault<Result>(sql, new{parm = "abcde"});
    }
  }
}

public class Result{
  public string Id {get; set;}
}

修正後コード

sqlの中身だけ変更。selectされる結果の型をconvertを使って変換してあげるだけ。

public class DataAccessObject{
  private const string sql = @"
declare @id uniqueidentifier
exec something_procedure @parm, @id output
select convert(varchar(50), @id) as Id
";

  public string GetId(){
    using (var conn = My.ConnectionFactory())
    {
      return conn.QueryFirstOrDefault<Result>(sql, new{parm = "abcde"});
    }
  }
}

public class Result{
  public string Id {get; set;}
}

学び

dapperは便利だけどマッピングできる型が無いとこういうことになる。
ちゃんと意図した型にマップされるか意識して使用すること。