Plugin-to-plugin communication via custom interfaces. Shows how plugins define, register, and consume services -- without the host needing to know about them.
CustomServiceDemo.exe
| DCC_UsePackage = rtl;fmx;FMXPluginFramework
|
+-- TBPLLoader.LoadAll(plugins.json)
|
+-- PluginProvider.bpl (required)
| +-- CustomService.Intf.pas -> defines IDataStore
| +-- PluginProvider.Main.pas -> implements + registers TDataStore
|
+-- PluginConsumer.bpl (required, requires PluginProvider)
| +-- PluginConsumer.Main.pas -> IPlugin + IFrameProvider
| +-- PluginConsumer.View.pas -> Frame with Key/Value UI
|
+-- MainForm
+-- TMemoLogger -> displays plugin logs
+-- Consumer frame embedded -> interacts with IDataStore
- Custom Interfaces: Plugins define their own interfaces with GUIDs
- TServiceRegistry as mediator: Provider registers, consumer retrieves -- without knowing each other directly
- BPL dependency chain: Consumer package has
requires PluginProviderin its.dpk - Interface unit rule:
CustomService.Intf.paslives in exactly one package (Provider). The consumer usesrequiresinstead ofcontainsto avoid duplicates - Frame embedding: Consumer provides a UI frame (IFrameProvider) that the host embeds
| File | Purpose |
|---|---|
CustomServiceDemo.dpr |
Host app (does not know about IDataStore!) |
Source/uMain.pas + .fmx |
MainForm with TMemoLogger + frame embedding |
CustomServiceDemo.groupproj |
Build: Framework -> Provider -> Consumer -> App |
plugins.json |
Both plugins as required |
../DemoPlugins/PluginProvider/ |
Defines + implements IDataStore |
../DemoPlugins/PluginConsumer/ |
Uses IDataStore, provides UI frame |
IDataStore = interface
['{F1A2B3C4-D5E6-4F7A-8B9C-0D1E2F3A4B5C}']
procedure SetValue(const AKey, AValue: string);
function GetValue(const AKey: string): string;
function GetAllKeys: TArray<string>;
procedure Clear;
end;- Host loads
PluginProvider.bplfirst (required: true) - Provider registers
TDataStoreasIDataStoreservice inInitialize - Host loads
PluginConsumer.bpl(BPL dependency:requires PluginProvider) - Consumer retrieves
IDataStoreviaGetServiceand provides a frame with Key/Value UI - Host embeds the consumer frame -- communication runs entirely between the plugins
- Host code knows neither
IDataStorenorCustomService.Intf-- purely a plugin concern