Created
May 19, 2015 01:24
-
-
Save worldspawn/c8472291e357c3ef29ba to your computer and use it in GitHub Desktop.
Protected+Audited domain actions
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.Collections.Generic; | |
using System.Linq; | |
using System.Text; | |
using System.Threading.Tasks; | |
namespace Manager | |
{ | |
class Program | |
{ | |
static void Main(string[] args) | |
{ | |
IDatabase database = null; | |
var managerFactory = new ManagerFactory(database); | |
var manager = managerFactory.Create<User>(); | |
var user = new User(); | |
manager.Manage(user, | |
new User.Tasks.ChangePassword("password")); | |
} | |
} | |
public class ManagerFactory | |
{ | |
private readonly IDatabase _database; | |
public ManagerFactory(IDatabase database) | |
{ | |
_database = database; | |
} | |
public Manager<TModel> Create<TModel>() | |
{ | |
return new Manager<TModel>(_database); | |
} | |
} | |
public interface IDatabase | |
{ | |
void Save(object obj); | |
void Save(object[] objects); | |
} | |
public class Manager<TModel> | |
{ | |
private readonly IDatabase _database; | |
public Manager(IDatabase database) | |
{ | |
_database = database; | |
} | |
public void Manage(TModel model, params ManagerTask<TModel>[] tasks) | |
{ | |
Manage(model, tasks.AsEnumerable()); | |
} | |
public void Manage(TModel model, IEnumerable<ManagerTask<TModel>> tasks) | |
{ | |
var audits = tasks.SelectMany(t => t.Run(model)); | |
_database.Save(audits); | |
} | |
} | |
public abstract class ManagerTask<TModel> | |
{ | |
public IEnumerable<TaskAudit> Run(TModel model) | |
{ | |
OnBeforeExecute(); | |
var audits = Execute(model); | |
OnAfterExecute(); | |
return audits; | |
} | |
protected virtual void OnBeforeExecute() | |
{ | |
} | |
protected abstract IEnumerable<TaskAudit> Execute(TModel model); | |
protected virtual void OnAfterExecute() | |
{ | |
} | |
} | |
public class TaskAudit | |
{ | |
public TaskAudit(object task, params TaskTarget[] targets) | |
{ | |
ExecutedAt = DateTime.UtcNow; | |
Task = task.GetType(); | |
Targets = targets; | |
} | |
public IEnumerable<TaskTarget> Targets { get; set; } | |
public Type Task { get; private set; } | |
public DateTime ExecutedAt { get; private set; } | |
public class TaskTarget | |
{ | |
public TaskTarget(Type type, Guid id) | |
{ | |
Type = type; | |
Id = id; | |
} | |
public Type Type { get; private set; } | |
public Guid Id { get; private set; } | |
public static implicit operator TaskTarget(Model model) | |
{ | |
return new TaskTarget(model.GetType(), model.Id); | |
} | |
} | |
} | |
public abstract class Model | |
{ | |
protected Model() | |
{ | |
} | |
protected Model(Guid id) | |
{ | |
Id = id; | |
} | |
public Guid Id { get; protected set; } | |
} | |
public class User : Model | |
{ | |
public User() | |
{ | |
} | |
public User(Guid id) : base(id) | |
{ | |
} | |
public string Password { get; private set; } | |
public static class Tasks | |
{ | |
public class ChangePassword : ManagerTask<User> | |
{ | |
private readonly string _password; | |
public ChangePassword(string password) | |
{ | |
_password = password; | |
} | |
protected override IEnumerable<TaskAudit> Execute(User model) | |
{ | |
model.Password = _password; | |
yield return new TaskAudit(this, model); | |
} | |
} | |
} | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment