Delphi-PRAXiS

Delphi-PRAXiS (https://www.delphipraxis.net/forum.php)
-   Algorithmen, Datenstrukturen und Klassendesign (https://www.delphipraxis.net/78-algorithmen-datenstrukturen-und-klassendesign/)
-   -   [Spring4D] Automatische Service-Liste mittels ResolveAll (https://www.delphipraxis.net/180515-%5Bspring4d%5D-automatische-service-liste-mittels-resolveall.html)

neo4a 26. Mai 2014 09:43


[Spring4D] Automatische Service-Liste mittels ResolveAll
 
Gibt es vielleicht einen eleganten Weg, die in Spring4D automatisch registrierten Typen/Componenten wieder zu listen, ohne eine zusätzliche Info-Struktur vorhalten zu müssen?

Mein modulares Programm hat folgende Struktur:

Delphi-Quellcode:
  IccApp = interface
  ['{D91CB460-F196-43C9-8633-4E5759164FB8}']
    function DisplayName : string;
  end;

  IccTestApp = interface(iccApp)
  ['{2CAC3397-B984-45BE-B255-56E5FD6220F5}']
    function BackstageView: TBackstageView;
    function ColorSchemeAccent : TColorSchemeAccent;
  end;

  TccApp_BackstageTest = class(TInterfacedObject, IccTestApp, IccApp) //das benötigt Spring4D, sonst gibt's einen Fehler
  private
    FBackstageBaseFormTest : TBackStageVM;
  private
    function DisplayName : string;
    function BackstageView: TBackstageView;
    function ColorSchemeAccent : TColorSchemeAccent;
  public
    constructor Create;
    destructor Destroy; override;
  end;

initialization
  GlobalContainer.RegisterType<TccApp_BackstageTest>.Implements<IccTestApp>.Implements<IccApp>;
Nun hätte ich gern die Möglichkeit, die auf diese Weise registrierten Typen nach Bedarf wieder "einzusammeln" und z.B. in einer Liste alle Services aufzuführen, die IccApp implementieren.

Weder
Delphi-Quellcode:
var
  aListArray : TArray<IccApp>;
  aItem : IccApp;
begin
  aListArray := GlobalContainer.ResolveAll<iccApp>;
  for aItem in aListArray do
    ShowMessage(aItem.DisplayName);
noch
Delphi-Quellcode:
var
  aListArray : TArray<TValue>;
  aItem : TValue;
begin
  aListArray := GlobalContainer.Context.ServiceResolver.ResolveAll(TypeInfo(iccApp));
  for aItem in aListArray do
    ShowMessage(aItem.AsType<IccApp>.DisplayName);
bringen mich so richtig weiter.

Stevie 26. Mai 2014 10:20

AW: [Spring4D] Automatische Service-Liste mittels ResolveAll
 
Die
Delphi-Quellcode:
IComponentRegistry
verfügt über alle Informationen zu den Registrierungen.

Delphi-Quellcode:
container.Context.ComponentRegistry.FindAll.Where(
  function(const model: TComponentModel): Boolean
  begin
    Result := model.HasService(TypeInfo(IccApp));
  end);
Allerdings wirst du so kaum an das Ergebnis von DisplayName kommen, denn dazu benötigst du ja eine Instanz.

ResolveAll bringt auch nur solche Services zurück, die mit einem Namen registriert wurden - siehe auch Issue 21 und Issue 22.

neo4a 26. Mai 2014 10:42

AW: [Spring4D] Automatische Service-Liste mittels ResolveAll
 
Danke, Stefan. Das bringt mich schon weiter.

Hat die Vergabe von Namen vielleicht noch weitere "magische" Effekte, die man praktisch nutzen kann?

[Edit]
Ich komme doch nicht allein weiter. Kannst Du bitte Dein obiges Code-Schnipsel exemplarisch so erweitern, dass eine Service-Instanz erstellt wird, deren Properties (z.B. DisplayName) dann zur weiteren Verfügung stehen.

Stevie 26. Mai 2014 11:02

AW: [Spring4D] Automatische Service-Liste mittels ResolveAll
 
Zitat:

Zitat von neo4a (Beitrag 1260224)
Danke, Stefan. Das bringt mich schon weiter.

Hat die Vergabe von Namen vielleicht noch weitere "magische" Effekte, die man praktisch nutzen kann?

Generell ist es so, dass:

- Resolve() die Default Registrierung zurückliefert - gibt es keine, wird eine Exception ausgelöst
- ResolveAll() alle Registrierungen mit Namen zurückliefert - gibt es keine, kommt ein leeres Ergebnis zurück

Eine Default Registrierung ist:

- die letzte Registrierung ohne Namen oder mit Angabe von .AsDefault

Zitat:

Zitat von neo4a (Beitrag 1260224)
[Edit]
Ich komme doch nicht allein weiter. Kannst Du bitte Dein obiges Code-Schnipsel exemplarisch so erweitern, dass eine Service-Instanz erstellt wird, deren Properties (z.B. DisplayName) dann zur weiteren Verfügung stehen.

Das Beispiel war nur, um an die Registrierungsinformationen zu kommen.

Vergib bei Implements<IccApp> einen Namen. Dann kannst du sie auch alle mit ResolveAll bekommen, so wie in deinem ersten Code Beispiel, was ich auch der empfohlene Weg ist (der ServiceResolver wird in Zukunft nämlich wegfallen, weil er mit dem DependencyResolver zusammen gelegt wird).

neo4a 26. Mai 2014 11:24

AW: [Spring4D] Automatische Service-Liste mittels ResolveAll
 
Zitat:

Zitat von Stevie (Beitrag 1260227)
Vergib bei Implements<IccApp> einen Namen. Dann kannst du sie auch alle mit ResolveAll bekommen, so wie in deinem ersten Code Beispiel

Danke. Das funktioniert nun wirklich gut und gibt mir die Möglichkeit, Registrierungs-Infos in den Klassen zu halten.


Alle Zeitangaben in WEZ +1. Es ist jetzt 02:49 Uhr.

Powered by vBulletin® Copyright ©2000 - 2024, Jelsoft Enterprises Ltd.
LinkBacks Enabled by vBSEO © 2011, Crawlability, Inc.
Delphi-PRAXiS (c) 2002 - 2023 by Daniel R. Wolf, 2024 by Thomas Breitkreuz