Передать тип переменной в метод без перечисления - PullRequest
0 голосов
/ 11 сентября 2009

Я хочу иметь возможность передавать тип переменной в метод, главным образом, чтобы я мог передать запрос структуры сущностей методу, который будет применять общие включения вложенного объекта.

Это то, что я хочу сделать ...

public Person GetPersonByID(int personID)
{
     var query = from Perspn p in Context.Persons
                 where p.PersonID = personID
                 select p;

     ObjectQuery<Person> personQuery = ApplyCommonIncludes<Person>(query);

     return personQuery.FirstOrDefault();
}


public ObjectQuery<T> ApplyCommonIncludes<T>(SomeType query)
{
     return ((ObjectQuery<T>)query)
          .Include("Orders")
          .Include("LoginHistory");
}

Ответы [ 2 ]

3 голосов
/ 11 сентября 2009

Кажется, вы действительно хотите, чтобы SomeType было ObjectQuery<T>, верно?

public ObjectQuery<T> ApplyCommonIncludes<T>(ObjectQuery<T> query)
{
     return query
          .Include("Orders")
          .Include("LoginHistory");
}

Это правильный синтаксис. Есть ли проблемы с этим?

Это должно работать и выполнять отложенное выполнение (я думаю, это то, что вы подразумеваете под "без перечисления"), пока не будет вызван FirstOrDefault ().

0 голосов
/ 17 сентября 2009

Я закончил тем, что создал другой подход. Мой репозиторий теперь содержит список строк, используемых для включений. Чтобы сохранить безопасность типов при создании включений, я создал следующий класс:

/// <summary>
/// Builds Includes
/// </summary>
public class IncludeBuilder
{
    /// <summary>
    /// List of parts for the Include
    /// </summary>
    private List<string> Parts;

    /// <summary>
    /// Creates a new IncludeBuilder
    /// </summary>
    private IncludeBuilder()
    {
        this.Parts = new List<string>();
    }


    /// <summary>
    /// Creates a new IncludeBuilder
    /// </summary>
    public static IncludeBuilder Create()
    {
        return new IncludeBuilder();
    }


    /// <summary>
    /// Adds a property name to the builder
    /// </summary>
    public IncludeBuilder AddPart<TEntity, TProp>(Expression<Func<TEntity, TProp>> expression)
    {
        string propName = ExpressionHelper.GetPropertyNameFromExpression(expression);
        this.Parts.Add(propName);

        return this;
    }


    /// <summary>
    /// Gets a value of the include parts separated by
    /// a decimal
    /// </summary>
    public override string ToString()
    {
        return string.Join(".", this.Parts.ToArray());

    }

Это позволяет мне сделать это ...

myPersonRepository.AppendInclude(
     IncludeBuilder.Create()
          .AddPart((Person p) => p.Orders)
          .AddPart((Order o) => o.Items));

Вышеприведенный оператор передает выражения в класс IncludeBuilder, который затем переводит вышеприведенное в «Orders.Items».

Затем я создал вспомогательные методы в моем RepositoryBase, которые дали ObjectQuery, применят включения, выполнят запрос и вернут результат. Не совсем то, что я искал, но хорошо работает.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...