Mi proyecto actual usa NHibernate 3.0b1 y la API NHibernate.Linq.Query<T>()
. Soy bastante fluido en LINQ, pero no tengo absolutamente ninguna experiencia con HQL o la API de ICriteria. Una de mis consultas no es compatible con la API IQueryable, así que supongo que necesito usar una de las API anteriores, pero no tengo idea de dónde empezar.¿Cómo expreso esta consulta LINQ utilizando la API de NHibernate ICriteria?
He intentado buscar en la web una buena guía de "inicio" para ICriteria, pero los únicos ejemplos que he encontrado son demasiado simplistas para aplicar aquí o demasiado avanzados para que los entendamos. Si alguien tiene algunos buenos materiales de aprendizaje para transmitir, sería muy apreciado.
En cualquier caso, el modelo de objetos de consulta que estoy en contra es similar al siguiente (en gran medida simplificados, propiedades no relevantes omitido):
class Ticket {
IEnumerable<TicketAction> Actions { get; set; }
}
abstract class TicketAction {
Person TakenBy { get; set; }
DateTime Timestamp { get; set; }
}
class CreateAction : TicketAction {}
class Person {
string Name { get; set; }
}
Un Ticket
tiene una colección de TicketAction
que describe su historia. TicketAction
subtipos incluyen CreateAction
, ReassignAction
, CloseAction
, etc. Todos los boletos tienen un CreateAction
agregado a esta colección cuando se creó.
Esta consulta LINQ está buscando tickets creados por alguien con el nombre dado.
var createdByName = "john".ToUpper();
var tickets = _session.Query<Ticket>()
.Where(t => t.Actions
.OfType<CreateAction>()
.Any(a => a.TakenBy.Name.ToUpper().Contains(createdByName));
El método OfType<T>()
provoca una NotSupportedException
a ser lanzado. ¿Puedo hacer esto usando ICriteria en su lugar?
prefiero no tener que añadir un respaldo referencia a una 'Ticket' de 'TicketAction' si puedo evitarlo, ya que eso introducirá otros problemas, pero gracias por la sugerencia. :) –
La otra forma en que manejamos situaciones como esta fue crear realmente el HQL en un generador de cadenas. Intentamos usar Linq para expresiones Nhibernate, pero tampoco admiten colecciones cuando la colección está en el lado del objeto. Desafortunadamente, el método "Contiene" no se traduce en Linq para nHibernate. – Josh
Fui con su sugerencia después de todo (agregando una referencia al ticket en TicketAction), pero termino con un error: "NHibernate.QueryException: could not resolve property: TakenBy.Nombre de: CreateAction " –