Dapper, ODATA e IQueryable in ASP.NET

asp.net-mvc dapper iqueryable mvvm odata

Domanda

Ho visto la grande prestazione di Dapper e alcuni esempi su come usarlo.

Mi chiedevo se posso usarlo per fornire dati IQueryable e integrarlo con il livello dell'interfaccia utente usando ODATA per trasferire i dati all'interfaccia utente (come griglie, elenchi, ...).

Esiste un modo per restituire gli oggetti Dapper AsQueryable invece di IEnumerable per eseguire query utilizzando ODATA?

Risposta accettata

No, non proprio. Bene, puoi avvolgere qualsiasi sequenza con. AsQueryable () se lo desideri, ma userà solo LINQ-to-Objects. Dapper è volutamente semplice; si cerca di fare ben poco, ma ciò che fa provare a farlo: lo fa maledettamente bene (anche se lo dico io). Un'interfaccia IQueryable corretta è l'esatto contrario di dapper ...


Risposta popolare

Recentemente mi sono trovato in questa situazione in cui volevo usare Dapper con OData ma non volevo usare Entity Framework per SQLite.

La mia soluzione era quella di creare un metodo di estensione per ODataQueryOptions in modo che i miei controller assomigliassero a questo

public IHttpActionResult GetDevices(ODataQueryOptions<User> queryOptions)
{
    var usersQuery = new UserQuery(page, perPage);
    var users = usersQuery.Search(queryOptions.WhereClause(), queryOptions.OrderByClause());
    return Ok<IEnumerable<User>>(users);
}

Questo sembra semplice e funziona per me finora, quindi mi ci sto attaccando. Dovevo solo limitare ciò che gli utenti possono filtrare per quanto riguarda l'odata

    protected ODataValidationSettings _validationSettings =
        new ODataValidationSettings
        {
            // These validation settings prevent anything except: (equals, and, or) filter and sorting
            AllowedFunctions = AllowedFunctions.None,
            AllowedLogicalOperators = AllowedLogicalOperators.Equal | AllowedLogicalOperators.And | AllowedLogicalOperators.Or | AllowedLogicalOperators.NotEqual,
            AllowedArithmeticOperators = AllowedArithmeticOperators.None,
            AllowedQueryOptions = AllowedQueryOptions.Filter | AllowedQueryOptions.OrderBy
        };

Ed ecco il metodo di estensione

    public static string WhereClause(this ODataQueryOptions options)
    {
        string s = "";
        if (options.Filter != null && options.Filter.FilterClause != null)
        {
            var node = options.Filter.FilterClause.Expression as BinaryOperatorNode;
            s = getWhereClause(node);
        }
        return s;
    }

    private static string getWhereClause(BinaryOperatorNode node)
    {
        // PARSE FILTER CLAUSE
        // Parsing a filter, e.g. /Users?$filter=Id eq '1' or Id eq '100'  
        var s = "";
        if (node.Left is SingleValuePropertyAccessNode && node.Right is ConstantNode)
        {
            var property = node.Left as SingleValuePropertyAccessNode ?? node.Right as SingleValuePropertyAccessNode;
            var constant = node.Left as ConstantNode ?? node.Right as ConstantNode;

            if (property != null && property.Property != null && constant != null && constant.Value != null)
            {
                s += $" {property.Property.Name} {getStringValue(node.OperatorKind)} '{constant.Value}' ";
            }
        }
        else
        {
            if (node.Left is BinaryOperatorNode)
                s += getWhereClause(node.Left as BinaryOperatorNode);

            if (node.Right is BinaryOperatorNode)
            {
                s += $" {getStringValue(node.OperatorKind)} ";
                s += getWhereClause(node.Right as BinaryOperatorNode);
            }
        }
        return s;
    }


Autorizzato sotto: CC-BY-SA with attribution
Non affiliato con Stack Overflow
È legale questo KB? Sì, impara il perché
Autorizzato sotto: CC-BY-SA with attribution
Non affiliato con Stack Overflow
È legale questo KB? Sì, impara il perché