Ist dies ein typischer Anwendungsfall für IOC?

Meine aktuelle Anwendung ermöglicht es Benutzern, benutzerdefinierte Webformulare über eine Reihe von Administratorbildschirmen zu definieren. Es handelt sich im Wesentlichen um eine Anwendung vom Typ EAV. Daher kann ich HTML- oder ASP.NET-Markups nicht hart codieren, um eine bestimmte Seite zu rendern. Stattdessen fordert die Benutzeroberfläche eine Instanz eines Formularobjekts von der Serviceschicht an, die wiederum ein Objekt mithilfe mehrerer RDMBS-Tabellen erstellt. Formular enthält die Art von Klassen, die Sie in einem solchen Kontext erwarten würden:Form=>IEnumerable<FormSections>=>IEnumerable<FormFields>

So sieht die Service-Schicht aus:

public class MyFormService: IFormService{

       public Form OpenForm(int formId){
          //construct and return a concrete implementation of Form 
       }
}

Alles funktioniert hervorragend (für eine Weile). Die Benutzeroberfläche macht sich keine Gedanken darüber, welche Abschnitte / Felder in einem bestimmten Formular vorhanden sind: Sie rendert das empfangene Formularobjekt problemlos in eine funktionierende ASP.NET-Seite.

Einige Wochen später erhalte ich eine neue Anforderung aus dem Unternehmen: Beim Anzeigen einer nicht bearbeitbaren (d. H. Schreibgeschützten) Version eines Formulars sollten bestimmte Feldwerte zusammengeführt und andere erfundene / berechnete Felder hinzugefügt werden. Kein Problem, sage ich. Ändern Sie einfach meine Serviceklasse, damit die Methoden expliziter sind:

public class MyFormService: IFormService{

       public Form  OpenFormForEditing(int formId){
          //construct and return a concrete implementation of Form 
       }

       public Form  OpenFormForViewing(int formId){
          //construct and a concrete implementation of Form  
          //apply additional transformations to the form
       }
}

Wieder funktioniert alles wunderbar und das Gleichgewicht ist wieder hergestellt. Die Benutzeroberfläche ist weiterhin agnostisch in Bezug auf das, was in der Form vorliegt, und unsere Trennung von Bedenken ist erreicht. Nur wenige Wochen später stellt das Unternehmen jedoch eine neue Anforderung: In bestimmten Szenarien sollten wir uns nur noch bewerbenetwas der Formtransformationen, auf die ich oben verwiesen habe.

An diesem Punkt scheint der Ansatz der "expliziten Methode" eine Sackgasse erreicht zu haben, es sei denn, ich möchte mit einer Explosion von Methoden enden (OpenFormViewingScenario1, OpenFormViewingScenario2 usw.). Stattdessen führe ich eine andere Indirektionsebene ein:

public interface IFormViewCreator{
        void CreateView(Form form);
}

public class MyFormService: IFormService{

       public Form  OpenFormForEditing(int formId){
          //construct and return a concrete implementation of Form 
       }

       public Form  OpenFormForViewing(int formId, IFormViewCreator formViewCreator){
          //construct a concrete implementation of Form  
          //apply transformations to the dynamic field list
           return formViewCreator.CreateView(form);
       }
}

Oberflächlich betrachtet scheint dies akzeptabel zu sein, und dennoch gibt es einen gewissen Geruch. Die Benutzeroberfläche, die bisher keine Ahnung von den Implementierungsdetails von OpenFormForViewing hatte, muss Kenntnisse über IFormViewCreator besitzen und eine Instanz von IFormViewCreator erstellen.

Ich habe zwei Fragen: Gibt es einen besseren Weg, um die gewünschte Kompositionsfähigkeit zu erreichen? (Vielleicht mithilfe eines IoC-Containers oder einer selbstgewalzten Fabrik, um den konkreten IFormViewCreator zu erstellen)?Habe ich die Abstraktion hier grundlegend vermasselt?

Antworten auf die Frage(2)

Ihre Antwort auf die Frage