Yes it is a violation of SRP as logging is a cross cutting concern.
The correct way is to delegate logging to a logger class (Interception) which sole purpose is to log - abiding by the SRP.
see this ling for a good example: https://msdn.microsoft.com/en-us/library/dn178467%28v=pandp.30%29.aspx
Here is a short example:
public interface ITenantStore
{
Tenant GetTenant(string tenant);
void SaveTenant(Tenant tenant);
}
public class TenantStore : ITenantStore
{
public Tenant GetTenant(string tenant)
{....}
public void SaveTenant(Tenant tenant)
{....}
}
public class TenantStoreLogger : ITenantStore
{
private readonly ILogger _logger; //dep inj
private readonly ITenantStore _tenantStore;
public TenantStoreLogger(ITenantStore tenantStore)
{
_tenantStore = tenantStore;
}
public Tenant GetTenant(string tenant)
{
_logger.Log("reading tenant " + tenant.id);
return _tenantStore.GetTenant(tenant);
}
public void SaveTenant(Tenant tenant)
{
_tenantStore.SaveTenant(tenant);
_logger.Log("saving tenant " + tenant.id);
}
}
Benefits include
- You can test this without logging - true unit testing
- you can easily toggle logging on / off - even at runtime
- you can substitute logging for other forms of logging, without ever having to change the TenantStore file.