0

I'm using Linq2db with a custom server-side only function:

[Sql.Function(Name = "UniqueValue", ServerSideOnly = true)]
public static int? UniqueValue( Expression<Func<ModelClass, string>> arg) {
            throw new NotSupportedException();
}

I then try to use it in a linq query with grouping:

var query = from a in context.data
                    group a by a.field1 into newgroup
                    select new {final = UniqueValue(row => row.field2) };

I then get "row => row.field2' cannot be converted to SQL." error at runtime.

I'm using SqlLite as the db, here is the the custom function:

[SQLiteFunction(Name = "UniqueValue", Arguments = 1, FuncType = FunctionType.Aggregate)]
    public class UniqueValue : SQLiteFunction {
        public override void Step(object[] args, int stepNumber, ref object contextData) {

        }

        public override object Final(object contextData) {
            return null;
        }
    }

Does anyone know how I can make a custom server-side only function work with grouping?

trs79
  • 309
  • 3
  • 13
  • 1
    I doubt the server function accepts a lambda (or equivalent) as a parameter. It probably should just be a `string`. – Jeff Mercado Apr 06 '16 at 19:49
  • I'm only using the lambda because I'm not sure how else to pass a column name to my unique function because of the group. I would like to be able to use something like "select UniqueValue(columnName)" – trs79 Apr 06 '16 at 19:54
  • What's the signature of the database function? – Gert Arnold Apr 06 '16 at 20:34
  • @Gert Arnold: Please see the updated description – trs79 Apr 06 '16 at 20:39

1 Answers1

0

Support for custom aggregate functions in linq2db was added in version 1.9.0. You need to define your function as custom aggregate like that:

[Sql.Function("UniqueValue", ServerSideOnly = true, IsAggregate = true, ArgIndices = new[]{0})]
public static TResult UniqueValue<TSource, TResult>(this IEnumerable<TSource> src, Expression<Func<TSource, TResult>> value)
    => throw new NotSupportedException();

and use:

var query = from a in context.data
    group a by new a.field1 into newgroup
    select new { final = newgroup.UniqueValue(row => row.field2) };