I used Repository pattern that I saw on online tutorial...
Everything works fine except for find method, I have no idea how to work with this and I'm having hard time understanding Expressions or Func types. I used linq and lambda before but I'm begginer and still don't use it fluently...
public IEnumerable<TEntity> Find(Expression<Func<TEntity, bool>> predicate)
{
return Context.Set<TEntity>().Where(predicate);
}
I have this model class:
public partial class Artikl
{
[Browsable(false)]
public int IDArtikli { get; set; }
public string Barkod { get; set; }
[DisplayName("Šifra")]
public Nullable<int> Sifra { get; set; }
public string Naziv { get; set; }
[DisplayName("JM")]
public string JedinicaMjere { get; set; }
public decimal Tarifa { get; set; }
[DisplayName("Prodajna")]
public Nullable<decimal> ProdajnaCijena { get; set; }
[Browsable(false)]
public Nullable<bool> Flag { get; set; }
public Nullable<decimal> Kalo { get; set; }
[DisplayName("Nabavna")]
public Nullable<decimal> NabavnaCijena { get; set; }
[DisplayName("Veleprodajna")]
public Nullable<decimal> VeleprodajnaCijena { get; set; }
public Nullable<decimal> Zalihe { get; set; }
}
My question is how can I get the Artikl item based on property "Sifra". I have no idea how to call this method...
private void txtSifra_TextChanged(object sender, EventArgs e)
{
var artikl = _UnitOfWork.Artikl.Find(???);
txtNaziv.Text = artikl.Naziv;
}
Other answers already explained how to use expression but I want to mention one thing that is often overlooked when using so-called repository pattern:
public IEnumerable<TEntity> Find(Expression<Func<TEntity, bool>> predicate)
{
return Context.Set<TEntity>().Where(predicate);
}
This returns IEnumerable<TEntity>
and because of that this:
var result = _UnitOfWork.Artikl.Find(c => c.Sifra == 1).FirstOrDefault()
Will not execute whole query in database. The database query will look (roughly) like this:
select * from Artikl where Sifra = 1 -- < not efficient
and not like this:
select top 1 * from Artikl where Sifra = 1 -- < efficient
To fix this issue you have to either return IQueryable
:
public IQueryable<TEntity> Find(Expression<Func<TEntity, bool>> predicate)
{
return Context.Set<TEntity>().Where(predicate);
}
Or make separate method for every query you are going to make:
public TEntity FindFirst(Expression<Func<TEntity, bool>> predicate)
{
return Context.Set<TEntity>().Where(predicate).FirstOrDefault();
}
You need to pass a lambda expression to satisfy Expression<Func<TEntity, bool>> predicate
. You can get the item based on property "Sifra" by doing this:
var artikl = _UnitOfWork.Artikl.Find(q => q.Sifra == "some int value").FirstOrDefault();
Hope it helps!
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With