Simplify LINQ code?
A few days ago a developer at a customer asked me how he could simplify the following code as he identified a pattern: X tries and the error handling.
public PlanungsGruppenLesenA PlanungsGruppenLesen(
PlanungsGruppenLesenF param)
{
PlanungsGruppenLesenA ret = new PlanungsGruppenLesenA();
if (ret.PlanungsGruppen == null)
{
throw new ArgumentNullException("param.PlanungsGruppen");
}
int nRetry = 0;
while (nRetry < DBWerkzeug.MaxWiederholungen)
{
try
{
using (XXX_POC.POC db =
new XXX_POC.POC(
DBWerkzeug.GetConnectionString()))
{
var q =
from p in db.Stammdaten_Planungsgruppe
orderby p.Name.ToLower()
select new PlanungsGruppeDM
{
ID = p.Rowid,
Name = p.Name
};
ret.PlanungsGruppen = q.ToList<PlanungsGruppeDM>();
}
}
catch (ChangeConflictException e)
{
nRetry++;
if (nRetry >= DBWerkzeug.MaxWiederholungen)
{
ret.FehlerText = e.Message;
ret.HatFehler = true;
throw;
}
}
catch (Exception e)
{
ret.FehlerText = e.Message;
ret.HatFehler = true;
throw;
}
}
return ret;
}
I ended up with this:
public PlanungsGruppenLesenA PlanungsGruppenLesen(
PlanungsGruppenLesenF param)
{
PlanungsGruppenLesenA ret = new PlanungsGruppenLesenA();
if (ret.PlanungsGruppen == null)
{
throw new ArgumentNullException("param.PlanungsGruppen");
}
ret.PlanungsGruppen = CatchExceptions<PlanungsGruppeDM>(
delegate
{
using (XXX_POC.POC db =
new XXX_POC.POC(
DBWerkzeug.GetConnectionString()))
{
var q =
from p in db.Stammdaten_Planungsgruppe
orderby p.Name.ToLower()
select new PlanungsGruppeDM
{
ID = p.Rowid,
Name = p.Name
};
return q.ToList<PlanungsGruppeDM>();
}
},
ret);
return ret;
}
What calls the encapsulated X tries and the error handling:
public delegate List<T> MachMal<T>();
public static List<T> CatchExceptions<T>(MachMal<T> machMichFertig, BasisA ret)
{
int nRetry = 0;
while (nRetry < DBWerkzeug.MaxWiederholungen)
{
try
{
return machMichFertig();
}
catch (ChangeConflictException e)
{
nRetry++;
if (nRetry >= DBWerkzeug.MaxWiederholungen)
{
ret.FehlerText = e.Message;
ret.HatFehler = true;
throw;
}
}
catch (Exception e)
{
ret.FehlerText = e.Message;
ret.HatFehler = true;
throw;
}
}
return null;
}
But I’m not quite sure If this made stuff really easier ;-)