Im looking for a way to increase productivity when I add a table to my database. Generally, when I add a new table I have to perform the following steps.
- Add table to the database (simple)
- Create the corresponding EF Code First class. (i dont use db migrations)
- Create a POCO model that matches the EF class created in #2.
- Create repository class
- Create Commands and Handlers for CQRS pattern
- Create AutoMapper maps for the newly created classes
I recently created a new website where the requirements were to use EF Database first and I saw how it was using the tt files to generate the classes. That got me thinking that I could somehow use those templates (new ones) to generate all the standard support items for basic CRUD operations. Trouble is I have no experience creating these templates and have no idea where to start.
Sample Code to be generated:
Repository
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
public interface IUsersRepository : IRepository<Users>
{
}
public class UsersRepository : RepositoryBase<Users>, IUsersRepository
{
public UsersRepository(IDatabaseFactory databaseFactory)
: base(databaseFactory)
{
}
}
Basic model based on entity generated from EDMX (or Code First)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
public class User
{
public int UserId { get; set; }
public string UserRole { get; set; }
public string UserName { get; set; }
}
Command
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
public class AddUpdateUserPayoutCommand : CommandBase, ICommand
{
public int UserId { get; set; }
public string UserRole { get; set; }
public string UserName { get; set; }
}
Command Handler
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
public class AddUpdateUserHandler: ICommandHandler<AddUpdateUserCommand>
{
private readonly IUsersRepository _repository;
private readonly IUnitOfWork _unitOfWork;
public AddUpdateUserPayoutHandler(IUsersRepository repository, IUnitOfWork unitOfWork)
{
_repository = repository;
_unitOfWork = unitOfWork;
}
public ICommandResult Execute(AddUpdateUserCommand command)
{
Users entity;
if (command.UserId == 0)
{
entity = AutoMapper.Mapper.Map<Users>(command);
_repository.Add(entity);
}
else
{
entity = _repository.Get(x=>x.UserId==command.UserId);
entity = AutoMapper.Mapper.Map<Users>(command);
_repository.Update(entity);
}
_unitOfWork.Commit(command.UserId);
return new CommandResult(true,entity.UserId);
}
}
Automapper Maps - Placed in app_start
Mapper.CreateMap<User, AddUpdateUserCommand>();
This example isn't meant to be a solution that one can cutnpaste into a project but as an example on how one could write a template that generate code from database schema.
Built a quick template to demonstrate how you might go about to generate the code artifacts.
You can find the whole project here: https://github.com/mrange/CodeStack/tree/master/q18787460/ModelGenerator
The template itself use T4Include.Schema to get the db schema. SMO is also completely legit to use as well, I just prefer T4Include.Schema because of the performance and that it only relies SqlConnection (T4Include.Schema is part of https://www.nuget.org/packages/T4IncludeTemplate/).
The basic strategy of the template is to get hold of all tables and iterate over them generating the code artifact.
Finally the generated code looks like this (for my test db that only has one table: CUS_Customer)
If you pull the project from github and update the connection string to something that is relevant to you it should generate the code for you. If you run into any issues just respond to this post.
What you want is in the road map of the Entity Interface Generator
https://entityinterfacegenerator.codeplex.com
This project contains customized T4 templates which can generate interfaces and attributes for the DbContext class and entity classes. It does not, but will soon, generate generic repositories.