Implement your adapter
- Last UpdatedAug 18, 2026
- 2 minute read
- PI System
- Adapter Framework 2.1.0
- Adapters
Implement the adapter-specific functionality required to communicate with your data source and publish data through the Adapter Framework. This includes configuring source connectivity, collecting data, mapping measurements, and implementing any required lifecycle behaviors.
Connect to your data source
Add the properties your adapter needs to connect, such as the host, port, credentials) to the DataSourceConfiguration.cs.
-
Implement Equals() and Validate() for it.
-
Be sure to include the [Protected] attribute on properties that hold sensitive information, such as passwords, connection strings, or API keys.
Define the data to collect
-
Add the properties you need to identify or select a data item. such as register address or field name) to DataSelectionItem.cs.
-
Add IEquatable<DataSelectionItem> and create a Validate()method.
Implement the adapter lifecycle
In the AdapterMain.cs, override the following methods as needed:
|
Method |
Purpose |
|---|---|
|
RegisterAdapterAsync |
Register custom configuration facets (when needed) and set the default stream ID pattern. |
|
InitializeAdapterAsync |
One-time adapter initialization. |
|
StartAdapterAsync |
Start collecting data - called once valid data source configuration exists. |
|
StopAdapterAsync |
Stop collecting data. |
|
ProcessDataSourceUpdateAsync |
React to data source configuration changes. |
|
ProcessSelectionUpdateAsync |
React to data selection configuration changes. |
|
GetDefaultStreamId |
Generate a default stream ID when none is configured. |
|
Dispose |
Clean up any resources allocated. |
Use the built-in scheduler (Optional)
If your adapter polls a data source on a scan-based interval rather than subscribing to it, use the built-in scheduler instead of writing your own timer or polling loop. It provides a reliable method to set scan rates and offers scan statistics (such as skipped scans, maximum scan time, and more) immediately.
-
Modify DataSelectionItem to implement IScanDataSelectionConfiguration to add a ScheduleId property rather than IDataSelectionConfiguration.
-
In the AdapterMain constructor, set EnableScheduling to true.
-
Instead of writing your own polling loop, override SampleDataAsync:
protected override async Task SampleDataAsync(string scheduleId, IReadOnlyList<DataSelectionItem> items, CancellationToken cancellationToken)
{
// Called whenever the schedule identified by scheduleId is due.
// items = the data selection items associated with that schedule.
}
-
After enabling, configure a Schedules facet (`Id`, `Period`, `Offset`) and assign each data selection item to a schedule through its ScheduleId.
Create types, streams, and send data
Before sending data values, the adapter must send the OMF type(s) and stream(s) at least once.
Use the common service methods available through CommonService (of type IAdapterCommonService) to build type/stream IDs, then send everything through the message processor:
MessageProcessor.WriteType(dataTypes);
MessageProcessor.WriteTypes(dataTypes);
MessageProcessor.WriteStream(dataStream);
MessageProcessor.WriteStreams(dataStreams);
MessageProcessor.WriteDynamicValue(selectionItem, value);
See the Sample adapter for additional details.