Sto lavorando a un collega per refactoring il seguente codice, sto cercando di trasformare questo in un'esperienza di insegnamento pure.
Codice originale
public class WidgetRepository
{
public Widget GetWidget(int id)
{
Widget widget;
if (HttpContext.Current != null)
{
widget = (Widget)HttpContext.Current.Cache["widget_" + id];
}
if (widget == null)
{
widget = GetWidgetImpl(id); // some db call
if (HttpContext.Current != null)
{
HttpContext.Current.Cache["widget_" + id] = widget;
}
}
return widget;
}
}
La cosa più ovvia che emerge è che il repository è a conoscenza dei concetti di ASP.NET, il che è particolarmente grave in quanto questo repository viene utilizzato dal codice non-ASP.NET in alcuni scenari.
Codice refactored
Ho deciso di rifattorizzare il codice come segue:
public class WidgetRepository
{
private readonly ICacheProvider _cacheProvider;
public WidgetRepository(ICacheProvider cacheProvider)
{
_cacheProvider = cacheProvider;
}
public Widget GetWidget(int id)
{
var widget = _cacheProvider.Get<Widget>("widget_" + id);
if (widget == null)
{
widget = GetWidgetImpl(id); // some db call
_cacheProvider.Add("widget_" + id, widget);
}
return widget;
}
}
public interface ICacheProvider
{
T Get<T>(string key);
void Add<T>(string key, T item);
}
public HttpCacheProvider : ICacheProvider
{
private readonly Cache _cache;
public HttpCacheProvider(Cache cache)
{
_cache = cache;
}
public T Get<T>(string key)
{
return (T)_cache[key];
}
public void Add<T>(string key, T item)
{
_cache[key] = item;
}
}
public NullCacheProvider : ICacheProvider
{
public T Get<T>(string key)
{
return null;
}
public void Add<T>(string key, T item)
{
}
}
La mia giustificazione
Ho spiegato i seguenti vantaggi al codice refactored:
-
Promuove Open / Close: possiamo cambiare l'implementazione della cache se vogliamo usare qualcos'altro in futuro (memcached, ecc.)
-
Minore complessità ciclomatica: meno istruzioni if
-
Non mescolare la tecnologia ASP.NET con la tecnologia di accesso ai dati
Rifiuti / dubbi
Tuttavia, ho ottenuto le seguenti confutazioni:
-
Non useremo una tecnologia di caching diversa nel prossimo futuro.
-
Sono più linee di codice (quindi è più complesso)
-
Devi impostare le dipendenze (la complessità viene spostata, non rimossa)
-
Esistono già tonnellate di codice che utilizzano
HttpContext.Current
, quindi questo codice non segue il pattern (anti-) esistente -
Stiamo ancora "utilizzando" ASP.NET all'interno del codice di accesso ai dati.
Le mie domande
Personalmente, trovo che i pro prevalgano sulle confutazioni, tuttavia, mi piacerebbe essere in grado di affrontare le confutazioni per aiutarli a educarli.
Le mie domande sono:
-
Sono giustificato nel fare il refactoring (supponendo che abbiamo tempo a disposizione per ripulire il codice)?
-
Come rispondo alle varie confutazioni?