title: "Discovery Services — Tag Discovery, DataLink, and Asset() Patterns" tags: [discovery-services, tagprovider, tag-discovery, datalink, linked-tags, dynamic-tags, asset-syntax, uns, iiot] description: "Understand the three connection patterns for external data in the UNS: Local Tags + Device Points, Linked Tags (DataLink), and Dynamic Tags (Asset). Learn when to use each, how Discovery Services extend the namespace, and the DataLink shortcut for hybrid workflows." version: "1.0" author: "Tatsoft"


Discovery Services — Tag Discovery, DataLink, and Asset() Patterns

FrameworX has two independent systems for getting external data into the Unified Namespace: the Device Module and Discovery Services. They share nothing architecturally. Some protocols (MQTT, OPC UA) are available in both, but the workflow and mental model are completely different. This skill teaches the three connection patterns and when to use each.

When to Use This Skill

Use when the user mentions or needs:

Do NOT use when:

Key Concept: Two Independent Systems

DEVICE MODULE                           DISCOVERY SERVICES
(Pillar 2: Devices)                     (Technology under Pillar 1: UNS)
?????????????????                       ????????????????????????????????
• Define local tags FIRST               • NO local tags needed
• Create Channel → Node → Points        • Give address, system discovers
• Explicit polling, scan rates           • On-demand, auto-managed
• ~100 protocols                         • ~17 protocols (discovery-capable)
• Full control, deterministic            • Dynamic, flexible
• Governance: LOCAL                      • Governance: EXTERNAL

Critical rule for AI: Never create UnsTags for data that will be accessed through Discovery Services dynamic tags. The whole point is zero local tags. Only create UnsTags when:

The Three Connection Patterns

These are not stages of development — they are three equally valid architectural patterns chosen based on data characteristics.

Pattern 1: Local Tags + Device Points (Traditional SCADA)

Define tags locally in UNS, then map them to physical device addresses through the Device Module.

When to use:

Configuration workflow:

  1. Create tags in UNS (UnsTags)
  2. Create Device Channel with protocol
  3. Create Device Node with station address
  4. Create Device Points mapping tags to addresses
  5. Configure AccessType for polling behavior

Access syntax: @Tag.FolderPath/TagName or Tag.FolderPath/TagName.Member

Modules involved: UNS (tags) + Devices (channel, node, points, access types)

Pattern 2: Linked Tags — DataLink Property (Hybrid)

Create local tags in UNS but set the DataLink property to a Discovery Services path. The runtime automatically manages communication — no Device Module configuration needed.

When to use:

Configuration workflow:

  1. Create tags in UNS (UnsTags)
  2. Set the DataLink property to the external path
  3. A Discovery Services connection for that protocol must exist
  4. Runtime auto-manages communication when the tag is accessed

DataLink field example:

Tag: Plant1/TankLevel
Type: Float
DataLink: /MQTT/plant/tank01/level

Access syntax: @Tag.Plant1/TankLevel — same as any local tag. The DataLink binding is transparent.

Key behavior:

Modules involved: UNS only (tags with DataLink). No Device Module tables.

Pattern 3: Dynamic Tags — Asset() Syntax (Zero Configuration)

Direct binding to external paths without creating any local tags. Discovery Services dynamically discovers and extends the UNS namespace. Tags are created in the real-time database (RTDB) on-demand when accessed.

When to use:

Configuration workflow:

  1. Create a Discovery Services connection (UnsTagProviders table) with protocol and address
  2. Optionally create an AssetTree folder linked to the connection
  3. Access data using Asset() syntax — tags appear dynamically

Access syntax:

// In scripts or expressions:
value = Asset("/ProviderName/path/to/variable")

// In display element bindings (LinkedValue field):
Asset(Client.Context.AssetPath + "/Temperature")

// Static path in display bindings:
@Tag.ProviderName.path.to.variable

Key behavior:

Modules involved: UNS (Discovery Services connection only). No tags, no devices.

Pattern Selection Guide

If your data...UseWhy
Requires deterministic polling with explicit scan ratesPattern 1 (Local Tags + Devices)Only way to control timing
Uses legacy/proprietary protocols without discoveryPattern 1Only option for non-discovery protocols
Needs local governance + alarms + historian, but flexible sourcingPattern 2 (DataLink)Best of both worlds
Has stable structure but multiple sites or changing sourcesPattern 2Template once, link many
Is temporary or diagnosticPattern 3 (Dynamic/Asset)No configuration overhead
Has unknown or changing structurePattern 3Dynamic discovery at runtime
Has thousands of tags, mostly for monitoringPattern 3Zero engineering per tag
Needs alarms on some points from a dynamic sourceMixed: Pattern 3 for browsing + Pattern 2 for alarm pointsUse DataLink for the critical subset

Most production systems use multiple patterns simultaneously. A typical split:

Discovery Services Connections (UnsTagProviders Table)

Supported Protocols for Tag Discovery

Only protocols with built-in discovery capability can be used. Currently 17 connectors:

ConnectorTypeNotes
AB Rockwell ControlLogixPLCDiscovers controller tags
Beckhoff TwinCATPLCDiscovers TwinCAT symbols
Canary HistorianHistorianAlso usable as Storage Location
Codesys PLC HandlerPLCDiscovers Codesys variables
DataHub Communication ServiceApplicationConnects to Cogent DataHub
FlowTimebaseDB DatabaseHistorianTime-series database
GE Proficy HistorianHistorianAlso usable as Storage Location
InfluxDB DatabaseHistorianAlso usable as Storage Location
LineMonitorApplicationProduction monitoring
MQTT ClientMessagingStandard MQTT broker
MQTT Sparkplug B CollectorMessagingSparkplugB-specific metadata
OPC UA ClientIndustrialStandard OPC UA discovery
OSIsoft Aveva PI SystemHistorianAlso usable as Storage Location
Server to ServerApplicationConnect to another FrameworX solution
SQL DatabaseDatabaseGeneric SQL data source
SQL Database NormalizedDatabaseNormalized schema variant

Important: The Device Module has ~100 protocols. Discovery Services has ~17. They are independent lists. Do not confuse them.

Historian Connectors — Dual Role

Some connectors (Canary, InfluxDB, GE Proficy, OSIsoft PI) serve two purposes:

  1. Tag Discovery — browse and read historical data, TrendCharts auto-query through Asset() syntax
  2. Storage Location — configured in Historian → Storage Locations as an archive target

When IsHistorian = true, TrendCharts using Asset() syntax automatically query the historian for time-range data.

Creating a Discovery Services Connection via MCP

get_table_schema('UnsTagProviders')
list_protocols('<protocol_name>')    // Get PrimaryStation format

Write example:

{
  "table_type": "UnsTagProviders",
  "data": [{
    "Name": "ProductionMQTT",
    "Protocol": "MQTT",
    "PrimaryStation": "localhost;1883;FrameworX-001;;;;;None;False;;AtLeastOnce;10;False;False;",
    "Separators": "BranchSeparator=/;AttributeSeparator=/;",
    "Description": "Production floor MQTT broker"
  }]
}

Key fields:

AssetTree Integration

The AssetTree makes Discovery Services data navigable in the UI. A linked folder connects an AssetTree node to a Discovery Services connection.

Creating Linked Folders via MCP

get_table_schema('UnsAssetTree')
{
  "table_type": "UnsAssetTree",
  "data": [{
    "Name": "Production/MQTTData",
    "TagProviderLink": "ProductionMQTT",
    "InitialBranch": "spBv1.0/GroupID",
    "Description": "MQTT production data linked to AssetTree"
  }]
}

From this folder down, the tree is dynamic — it auto-expands based on what the Discovery Services connection discovers at runtime.

When the user clicks a node in an AssetsTree control:

Asset() Syntax Reference

Basic Usage

// Read a value
double temp = TK.ToDouble(Asset("/ProviderName/path/to/temperature"));

// Write a value
Asset("/ProviderName/path/to/setpoint") = 75.0;

// Dynamic path from context (in display CodeBehind)
double val = TK.ToDouble(Asset(@Client.Context.AssetPath + "/Temperature"));

Data Type Handling

WPF (.NET Framework 4.8) — automatic type resolution works.

HTML5/Portable (NetStandard 2.0) — explicit conversion required:

int intValue    = TK.ToInt(Asset("/path"));
double dblValue = TK.ToDouble(Asset("/path"));
string strValue = TK.ToString(Asset("/path"));
bool boolValue  = TK.ToDigital(Asset("/path"));

Asset() vs Tag Syntax

SyntaxWhen to useExample
@Tag.Folder/NameLocal tags, Linked Tags (DataLink)@Tag.Plant1/TankLevel
Asset("path")Dynamic tags from Discovery ServicesAsset("/MQTT/plant/tank01/level")
Asset(expression)Dynamic UIs driven by user selectionAsset(Client.Context.AssetPath + "/Temp")

Note: Asset() also works with local tags. It's sometimes used even with local tags because the string argument can be an expression, enabling dynamic display patterns.

Common Pitfalls

MistakeWhy it happensHow to avoid
Creating UnsTags for dynamic Discovery Services dataHabit from Device Module workflowDynamic tags don't need local tags — that's the whole point. Only create UnsTags if you need alarms/historian or want DataLink.
Confusing Device Module protocols with Discovery Services protocolsBoth can use MQTT/OPC UADevice Module has ~100 protocols. Discovery Services has ~17. Check list_protocols() for Discovery Services availability.
Setting alarms on dynamic tagsDynamic tags have no local tag to attach alarms toCreate a local tag with DataLink to the specific path, then configure alarms on that tag.
Using DataLink without a Discovery Services connectionDataLink needs the underlying TagProvider technologyA UnsTagProviders entry for the matching protocol must exist. DataLink binds to paths in that connection.
Thinking Discovery Services replaces DevicesThey are independent systemsBoth can coexist in the same solution. Use Devices for control, Discovery Services for monitoring/IoT.
Wrong PrimaryStation formatEach protocol has its own formatAlways call list_protocols('<protocol>') before writing UnsTagProviders.

Mixed-Mode Example

A typical production solution combining all three patterns:

UNS Tags:
  Safety/EStop          → Device Module (Modbus, deterministic polling)
  Safety/FireAlarm      → Device Module (Modbus)
  Production/LineSpeed  → DataLink: /MQTT/plant/line1/speed  (local tag + auto-comm)
  Production/OEE        → DataLink: /MQTT/plant/line1/oee
  Quality/BatchResult   → DataLink: /OPC/mes/quality/result

Discovery Services Connections:
  MQTT (ProductionMQTT) → mqtt.factory.local:1883
  OPC  (MESServer)      → opc.tcp://mes:4840

AssetTree:
  Plant/
    Safety/         → manual tags, Device Module
    Production/     → linked to ProductionMQTT via AssetTree folder
    Enterprise/     → linked to MESServer, browsed via Asset() syntax

In this setup, safety tags have full deterministic control, production tags have local governance with auto-managed communication, and enterprise data flows dynamically with zero tag engineering.

Related Skills

Documentation References