Data annotations on models when there are multiple repository implementations - c#

My DTOs are pretty simple classes.
public class PlainClass {
public int Id { get; set; }
public string Name { get; set; }
public List<PlainSubClass> SubObjects { get; set; }
}
public class PlainSubClass {
public int Id { get; set; }
public string Name { get; set; }
}
I have a repository interface, whose implementations are meant to retrieve data.
public interface IRepository
{
IEnumerable<PlainClass> PlainObjects { get; }
}
Now, I want to implement that interface in another class mocking the database and also using EF SQLite, and possibly more in the future. My mock is simple but, in trying to implement and then generate the database I'm getting an error back stating I need to designate a primary key.
Now, how should I go about doing that? Should I build out interfaces for my models and add annotations specific to each implementation? Should I -- if it's even possible -- add multiple sets of annotations to the models?

Related

Stop EF Inheritance

I have threeType MaliOp, LoanEBD, PrmEBD
public class MaliOp
{
public int Id { get; set; }
public int OldId { get; set; }
public byte MaliTable { get; set; }
public string Date { get; set; }
public short OpState { get; set; }
}
public class LoanEBD : MaliOp
{
public int? BId { get; set; }
public int? Loan { get; set; }
public int? PayerBimeGozar { get; set; }
[NotMapped]
public int OldId { get; set; }
}
public class PrmEBD : MaliOp
{
public int? PayerBimeGozar { get; set; }
public int? BId { get; set; }
[NotMapped]
public int OldId { get; set; }
}
the two Entity PrmEBD and LoanEBD Inherit from MaliOp. I want create DBContext in Entity Framework by by using this three types.
I have three Table in Database fro each one of them.
I don't want to use any EF Inhertance Strategy and add each one as Independent Types. but can't and EF Use either one of Inhertance strategy.
How can I do that?
create a IMaliOp Interface and let MaliOp implement it.
let the two classes implement the IMaliOp interface as well
Then use automapper (or something similar) to automatically transfer the information from the Entity object to your regular object.
This two classes would represent DTO (data transfer object). there are many strategies, out there for DTO-s
You should avoid having Classes inherit Entities, otherwise you applications classes will get too tightly coupled, and changes might prove them self to become too painful
In your context, override OnModelCreating;
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<PrmEBD>().ToTable("PrmEBDs");
modelBuilder.Entity<LoanEBD>().ToTable("LoanEBD");
modelBuilder.Entity<MaliOp>().ToTable("MaliOp");
}
This will create three separate tables in your database.
You will need to make sure that when you do a query over MaliOp, that you don't pull in instances from all three tables. You may want to go wit the approach of creating a common interface for all three, so that they don't actually inherit from each other, too

Wcf data service projections and query methods

I'm quite familiar with RIA Services, but not with WCF Data Services, and I'm wondering how to do something in the latter which I know how to do in the former.
I know examples for each data access methods on how to query database entities when the data service is backed by entity framework (or something similar).
But often enough I want to offer a queryable service method that isn't based on any database entity directly. It could be a combination from several database entities, an inherent grouping, or simply a database entity together with some additional, computed data.
Let's say I have the following classes:
// part of the model
class SomeEntity
{
public Guid Id { get; set; }
public String PropertyA { get; set; }
public String PropertyB { get; set; }
public Guid SubsidiaryKey { get; set; }
public virtual SomeSubsidiaryEntity Subsidiary { get; set; }
public virtual ICollection<SomeRelatedEntity> RelatedEntities { get; set; }
}
// part of the model
class SomeSubsidiaryEntity
{
public Guid Id { get; set; }
public String PropertyS { get; set; }
}
// not part of the model, exists only for the service layer
class SomeEntityProjection
{
public Guid Id { get; set; }
public String PropertyA { get; set; }
public String PropertyB { get; set; }
public String PropertyS { get; set; }
public Int32 RelatedEntitiesCount { get; set; }
}
The first two are part of the database model the service is using, the last is a projection entity.
The projection entity isn't part of the database - it only exists in the service layer.
With RIA Services, I can now write a query function like this:
public IQueryable<SomeEntityProjection> GetSomeEntitiesWithSomeFluff()
{
return
from e in this.DbContext.SomeEntities
select new SomeEntityProjection()
{
PropertyA = e.PropertyA,
PropertyB = e.PropertyB,
PropertyS = e.Subsidiary.PropertyS,
RelatedEntitiesCount = e.RelatedEntities.Count()
}
}
The data service method then supports client-side filtering and sorting for all four properties. All such client-side sorting and filtering will be properly delegated to the database and done there.
I couldn't find any examples of this for WCF Data Services, so my question is: Is this possible with WCF Data Services also and if so, how to do it?
You would use Data Transfer Objects (DTO) across the wire, which are similar, but not necessarily identical to your entity objects. That way they can vary independently.

How to store two same entities in a database? Entity framework, c#

I have two entities with exactly the same properties:
public class Oil
{
public Guid Id { get; set; }
public string Title { get; set; }
public int Price { get; set; }
public int Ammount { get; set; }
}
public class Filter
{
public Guid Id { get; set; }
public string Title { get; set; }
public int Price { get; set; }
public int Ammount { get; set; }
}
Questions:
1) Can I somehow store them in one table? If so, than how?
2) Or should I implement inheritance? And what type then?
Edits:
In my case these two entities are just the same, they will not have any different properties in the future.
I implemented Table-per-Hierarchy approach, but there is another issue
(I have another type that has collections of oils and filters):
public class Warehouse
{
public Guid Id { get; set; }
public ICollection<Filter> Filters { get; set; }
public ICollection<Oil> Oils { get; set; }
}
So, when I create database, I get Warehouse_Id and Warehouse_Id1 fields in it. I don't want the Oil and Filter classes to have Warehouse property in them, how can I get just one field for Warehouse id in the db table?
If I include WarehouseId as a property in OilFilterBase class I will get 3 warehouse_id in the database table.
p.s. I also have DbSet<Oil> and DbSet<Filter> in my Context and don't have DbSet<OilFilterBase>.
It's hard to say what's best without knowing more about your requirements. What makes these two entities different? If they perform different functions and just happen to have the same properties, then it would probably be a good idea to store them in separate tables; that makes the most sense conceptually, and it would make things much easier if, say, you decided you wanted to add additional properties to one of them in the future.
On the other hand, if they're really the same at every level, it's also worth asking if you really need two different entity types to store them.
For the middle ground where the two classes serve related purposes but also differ in some ways, then yes, some form of inheritance might be a good approach -- either having one entity type derive from the other, or creating a new common base type and having both entities derive from that.
If you decide this is the best approach, then it looks like a good candidate for Table-per-Hierarchy mapping. You could restructure your code something like this:
public abstract class OilFilterBase
{
public Guid Id { get; set; }
public string Title { get; set; }
public int Price { get; set; }
public int Amount { get; set; }
}
public class Oil : OilFilterBase
{
}
public class Filter : OilFilterBase
{
}
...and then the Entity Framework will, by default, create a single table with an automatically-generated discriminator column, and store all instances of both entity types in that table.
If you decide that either of those entity types should have additional fields, then you could look at some of the other inheritance options, like Table-per-Type, that create separate but related tables for each entity type.
The first thing to do is decide how these classes fit together conceptually, and then figure out the best way to implement that in EF terms. If you can give more information about what these entities are and how they work, it'll be easier for people here to give good advice.
Response to Edits:
I think what's happening with the extra columns (Warehouse_Id and Warehouse_Id1) is this:
Because you're setting up the relationships for Oil and Filter separately, it's not comfortable assuming you want to use the base class's WarehouseId property as the foreign key -- what if you only wanted to set up that relationship for Oil and not Filter? It shouldn't be writing to the base class column in that case. So, it decides to create new properties instead.
Fortunately, you can use the [ForeignKey()] attribute (or the fluent API) to tell it what you really want, like this:
using System.ComponentModel.DataAnnotations.Schema;
public abstract class OilFilterBase
{
public Guid Id { get; set; }
public string Title { get; set; }
public int Price { get; set; }
public int Amount { get; set; }
public Guid WarehouseId { get; set; }
}
public class Oil : OilFilterBase
{
}
public class Filter : OilFilterBase
{
}
public class Warehouse
{
public Guid Id { get; set; }
[ForeignKey("WarehouseId")]
public virtual ICollection<Filter> Filters { get; set; }
[ForeignKey("WarehouseId")]
public virtual ICollection<Oil> Oils { get; set; }
}
Also, I think you'll need to include a DbSet<OilFilterBase> (in addition to DbSet<Oil> and DbSet<Filter>) in your context in order to get Table-per-Hierarchy inheritance to work -- try it and see.
Good luck!

Model and partial model, how to avoid the redundant code?

I have a model and a partial model which contains only the properties that I need to expose in JSON.
But the properties between the model and his partial model are redundant.
How can I avoid that or improve my approach?
namespace Dashboard.Models.UserModels
{
public class UserModel
{
public int id { get; set; }
public string dbName { get; set; }
public string firstname { get; set; }
public string lastname { get; set; }
public int idExternal { get; set; }
public int idInstance { get; set; }
public string login { get; set; }
public string password { get; set; }
public DateTime? dtContractStart { get; set; }
public DateTime? dtContractEnd { get; set; }
public string emailPro { get; set; }
public string emailPerso { get; set; }
public LuccaUserModel()
{
idInstance = -1;
}
// partial model for json result
// not sure is the best way or have to be here
public class PartialUserModel
{
public int id { get; set; }
public string firstname { get; set; }
public string lastname { get; set; }
public string emailPro { get; set; }
public string emailPerso { get; set; }
public DateTime? dtContractStart { get; set; }
public DateTime? dtContractEnd { get; set; }
public string url { get; set; }
}
// UserModel Methods
}
}
You can rename PartialUserModel UserModelBase class (or leave it as is... it just makes better logical sense to do so) and make UserModel to inherit from it:
public class UserModel : UserModelBase
{
...
}
Of course you'll need to remove all duplicate properties from UserModel in this case.
It's a thin line between doing a proper design and building an overkill design. Answer depends on many inputs, among which I chose to have project and model breadth most important.
In hope to have my answer clearer, I have to say I use different terminology. Data which is adopted for use in UI is usually called ViewModel. In your case, you would build UserViewModel which contains necessary subset of information.
If I'm working on a one-off project, I'll reuse model as a ViewModel. I'll do this by having helper method which removes sensitive information, loads up or cuts off data which is lazy loaded from database and does other preparation on data. All this is done with same model class.
If it's not a short term project, I look to create separate ViewModel classes which I map from model data. Then, if I'm working with mostly flat data I use AutoMapper tool to have data automatically copied, instead of writing my own mappers.
As another answer here states, you write a basic class with data you need in UI and extend it with other model data, however this is not a good approach for several reasons.
If violates separation of concerns. Project dealing with model and persistance should not know about your ViewModel
You may need to flatten data from related objects into ViewModel objects. In that case, your model objects would have fields which should not be there, or would be redundant.
You may need calculated fields and helper methods in ViewModel which would again end up in model, confusing everyone that is not updated about design.
You could want to adopt several unrelated model classes to same ViewModel class
To try and put it shortly, either reuse model class or create ViewModels. There is unfortunately no clever solution. If you find one, please post a comment as I'd like to hear about it :)

How to create a DTO in asp.net?

1) I want to know what is the recommended way to create & return a DTO for an object which has 10 attributes and I only want to return 2 with my DTO object.
2) Should DTO's have their own namespace ? If yes, how do we organize them ? Each DTO inside a single class file or all DTO's inside a single class ?
Please provide me some sample code.
DTOs are dumb objects composed of public getters/setters. I generally put them in a separate namespace called SomeProject.Dto.
public class CustomerDto {
public int Id { get; set; }
public string Name { get; set; }
public LocationDto HomeAddress { get; set; }
}
I generally try to keep the property names the same between the DTO and corresponding domain class, possibly with some flattening. For example, my Customer might have an Address object, but my DTO might have that flattened to:
public class CustomerDto {
public int Id { get; set; }
public string Name { get; set; }
public string HomeStreet { get; set; }
public string HomeCity { get; set; }
public string HomeProvince { get; set; }
public string HomeCountry { get; set; }
public string HomePostalCode { get; set; }
}
You can dramatically reduce the amount of repetitive mapping code of translating domain objects into DTOs by using Jimmy Bogard's AutoMapper.
http://automapper.codeplex.com/
Your question is very open ended. The answers are dependent on the scale of your application.
In general I create my DTO's or ViewModels in their own assembly. To get my DTO's I have some service layer take care of creating them based on my request.
If you want concrete examples take a look at some of the Asp.NET MVC examples at asp.net. While you may not be using MVC you can at least see how the ViewModels are created.

Categories

Resources