Reputation: 7684
How can I achieve something like the following?
public interface IGenericRepository
{
int id { get; }
T GetById<T>() where T : class
}
public class GenericRepository : IGenericRepository
{
//Some code here
public T GetById<T>(int tid) where T : class
{
return from tbl in dataContext.GetTable<T> where tbl.id == tid select tbl;
}
}
And I would like to use this as follows:
GenericRepository gr = new GenericRepository();
Category cat = gr.GetById<Category>(15);
Of course, in this usage, tbl.id
in the GenericRepository gives me an error.
SOLUTION
public class IHasId
{
public int id { get; set; }
}
public interface IGenericRepository
{
int id { get; }
T GetById<T>(int id) where T : IHasId;
}
public class GenericRepository : IGenericRepository
{
public int id
{
get { throw new NotImplementedException(); }
}
public T GetById<T>(int id) where T : IHasId
{
return from tbl in dataContext.GetTable<T> where tbl.id == tid select tbl;
}
}
And apart from these, DON'T forget to define this somewhere in your model:
public partial class Category : IHasId { }
And the usage is:
Repository rep = new Repository();
Category cat = rep.GetById<Category>(15);
Upvotes: 0
Views: 937
Reputation: 60516
You get this error because you accept every class where T : class
. A class don't have that property.
Create an abstract class or interface to make sure that this property exists and change where T : class
to where T : IHasIdProperty
.
Upvotes: 1
Reputation: 60516
public class IHasId
{
public int id { get; set; }
}
public interface IGenericRepository<T>
{
int id { get; }
T GetById(int id);
}
public class GenericRepository<T> : IGenericRepository<T> where T : IHasId
{
public int id
{
get { throw new NotImplementedException(); }
}
public T GetById(int id)
{
return from tbl in dataContext.GetTable<T> where tbl.id == tid select tbl;
}
}
Upvotes: 1
Reputation: 3621
There's a few problems here - the first is that the generic type you're matching is a class, but a class doesn't have a property called 'id'. You need to have your Category class implement an interface that exposes an 'id' property:
public interface IIdentity
{
int identity { get; set; }
}
public class Category : IIdentity
{
public int identity{ get; set; }
}
I don't know why you've exposed 'id' as a property on the IGenericRepository interface - surely this is supposed to be a parameter passed to the find method (as indicated by your implementation). You also need to change the restriction on the 'GetById' method from:
where T : class
to something like
where T : IIdentity
using the interface I've suggested above.
Upvotes: 2