C
C#9mo ago
Omnissiah

✅ Reengineering repository layer

I'm trying to bring a code base that was left to me to a more modern architecture. I'm at the point where I need to deal with the repositories because they are becoming a problem. Creating new classes for manipulating data and re-reouting the flow of the code in the current architecture shouldn't be that much of a problem, but I have some difficulties in understading how to organize code for some common operations. What I mean is: currently models have some common logic, let's take auditing for example. When a model is created or updated I need to set who did it and when. Stuff like:
[Serializable]
public abstract class AuditedEntity : OtherAuditing
{
/// <inheritdoc />
public virtual DateTime? LastModificationTime { get; set; }

/// <inheritdoc />
public virtual Guid? LastModifierId { get; set; }
}
public class SomeModel : AuditedEntity { }
public class OtherModel : AuditedEntity { }
[Serializable]
public abstract class AuditedEntity : OtherAuditing
{
/// <inheritdoc />
public virtual DateTime? LastModificationTime { get; set; }

/// <inheritdoc />
public virtual Guid? LastModifierId { get; set; }
}
public class SomeModel : AuditedEntity { }
public class OtherModel : AuditedEntity { }
I would set these fields once per operation (or say unit of work), seems the reasonable thing to do, but what would be a way to do it? The only thing I could think of is having a class with specifically an isolated method for this that I call manually every time I touch a model that is audited. Maybe I could get all the tracked models in the current context from ef and if any inherits from AuditedEntity I update its fields, but that's a little ugly. The other stuff I could come up with would be even uglier. Am I looking at this the wrong way? The solutions I found searching around are either too old or for bigger projects (this is in the 100_000s of lines) and it would be probably too much to maintain,
4 Replies
Saber
Saber9mo ago
Assuming your using EF, you can use a SaveChangesInterceptor to update those fields before saving
Omnissiah
OmnissiahOP9mo ago
i'm on net 7 + ef core interesting, but i will admit that a behavior like this worries me a little, i'm not yet at the point where i'd want stuff to be this much automatic because it could screw up something there is also another point which would be that auditing is the easy stuff; i have yet to check if there is any more complicated logic, and i would prepare to the fact that SaveChangesInterceptor could not be the most appropriate place for it
Saber
Saber9mo ago
Well you should figure out those concerns then as an interceptor is very common for something simple like this
Omnissiah
OmnissiahOP9mo ago
my first thought would have been something like an inherited class that has a base method that you have to call to save to db that updates the model in this context you can't really do this anymore, but the pro is that it would be immediately understandable to anyone who would look at the code an interceptor/middleware that is configured in another part of the code is not self-explanatory, that's why it worries me which again for a simple feature like auditing it would be fine, although i don't really know how it works yet, but i suppose it is but if i find some more complicated logic i have to make clear that it's there, i kind of have to create a service for it to next time
Want results from more Discord servers?
Add your server